Skip to content

Commit 0f3a422

Browse files
committed
deploy: 8a905e4
1 parent 9388fe3 commit 0f3a422

File tree

35 files changed

+592
-89
lines changed

35 files changed

+592
-89
lines changed

LiveDevelopment/BrowserScripts/pageLoaderWorker.js

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -106,12 +106,13 @@ let messageQueue = [];
106106
function _sendMessage(message) {
107107
if(_livePreviewWebSocket && _livePreviewWebSocketOpen) {
108108
_livePreviewWebSocket.send(mergeMetadataAndArrayBuffer(message));
109-
return;
110109
} else if(_livePreviewNavigationChannel){
111110
_livePreviewNavigationChannel.postMessage(message);
111+
} else {
112+
console.warn("No Channels available for live preview worker messaging," +
113+
" queueing request, waiting for channel..");
114+
messageQueue.push(message);
112115
}
113-
console.warn("No Channels available for live preview worker messaging, queueing request, waiting for channel..");
114-
messageQueue.push(message);
115116
}
116117

117118
function flushPendingMessages() {

appConfig.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ window.AppConfig = {
2323
"extension_store_url": "https://store.core.ai/src/",
2424
"app_notification_url": "assets/notifications/dev/",
2525
"linting.enabled_by_default": true,
26-
"build_timestamp": "2024-01-11T03:28:47.685Z",
26+
"build_timestamp": "2024-01-11T11:57:33.555Z",
2727
"googleAnalyticsID": "G-P4HJFPDB76",
2828
"googleAnalyticsIDDesktop": "G-VE5BXWJ0HF",
2929
"mixPanelID": "49c4d164b592be2350fc7af06a259bf3",
@@ -34,7 +34,7 @@ window.AppConfig = {
3434
"bugsnagEnv": "development"
3535
},
3636
"name": "Phoenix",
37-
"version": "3.2.17-19689",
37+
"version": "3.2.17-19694",
3838
"apiVersion": "3.2.17",
3939
"homepage": "https://core.ai",
4040
"issues": {

assets/default-project/en.zip

0 Bytes
Binary file not shown.

assets/sample-projects/HTML5.zip

0 Bytes
Binary file not shown.
0 Bytes
Binary file not shown.
0 Bytes
Binary file not shown.

assets/sample-projects/explore.zip

0 Bytes
Binary file not shown.
0 Bytes
Binary file not shown.

brackets-min.js

Lines changed: 107 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -12825,7 +12825,7 @@ define("document/DocumentCommandHandlers", function (require, exports, module) {
1282512825
if (doc.isUntitled()) {
1282612826
return fullPath.substring(fullPath.lastIndexOf("/") + 1);
1282712827
}
12828-
return ProjectManager.makeProjectRelativeIfPossible(fullPath);
12828+
return Phoenix.app.getDisplayPath(ProjectManager.makeProjectRelativeIfPossible(fullPath));
1282912829

1283012830
}
1283112831

@@ -12841,7 +12841,8 @@ define("document/DocumentCommandHandlers", function (require, exports, module) {
1284112841
if (newDocument) {
1284212842
_currentTitlePath = _shortTitleForDocument(newDocument);
1284312843
} else {
12844-
_currentTitlePath = ProjectManager.makeProjectRelativeIfPossible(newFile.fullPath);
12844+
const filePath = ProjectManager.makeProjectRelativeIfPossible(newFile.fullPath);
12845+
_currentTitlePath = Phoenix.app.getDisplayPath(filePath);
1284512846
}
1284612847
} else {
1284712848
_currentTitlePath = null;
@@ -31323,15 +31324,18 @@ table tr{background-color:#fff;border-top:1px solid #c6cbd1}table tr:nth-child(2
3132331324
let _staticServerInstance;
3132431325
let projectServerPort = 0;
3132531326

31326-
function getNoPreviewURL(){
31327+
function getNoPreviewURL(
31328+
heading = Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW,
31329+
message = Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW_DETAILS
31330+
){
3132731331
if(!staticServerURL){
3132831332
return `${window.Phoenix.baseURL}assets/phoenix-splash/no-preview.html?jsonInput=`+
31329-
encodeURIComponent(`{"heading":"${Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW}",`
31330-
+`"details":"${Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW_DETAILS}"}`);
31333+
encodeURIComponent(`{"heading":"${heading}",`
31334+
+`"details":"${message}"}`);
3133131335
}
3133231336
return `${staticServerURL}phoenix-splash/no-preview.html?jsonInput=`+
31333-
encodeURIComponent(`{"heading":"${Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW}",`
31334-
+`"details":"${Strings.DESCRIPTION_LIVEDEV_NO_PREVIEW_DETAILS}"}`);
31337+
encodeURIComponent(`{"heading":"${heading}",`
31338+
+`"details":"${message}"}`);
3133531339
}
3133631340

3133731341
async function tabLoaderOnline(data) {
@@ -31664,7 +31668,75 @@ table tr{background-color:#fff;border-top:1px solid #c6cbd1}table tr:nth-child(2
3166431668
return _staticServerInstance._getInstrumentedContent(filePath, url);
3166531669
}
3166631670
return Promise.reject("Cannot get content");
31667-
};
31671+
}
31672+
31673+
/*getExternalContent - Special Live Preview for External Project Files
31674+
------------------------------------------------
31675+
Overview:
31676+
- This feature allows for the preview of files that are not part of the current project.
31677+
It's specifically for files that users open in the editor but which are outside the scope
31678+
of the project being worked on. Useful when users want to quickly view or edit files that are not
31679+
part of the project without integrating them into the project's environment.
31680+
31681+
Domain Separation:
31682+
- The previews for these external files are loaded from a static server URL, not the usual live preview
31683+
server URL.
31684+
- This separation ensures that the active live preview environment does not have access to resources
31685+
from external projects.
31686+
31687+
Security Measures:
31688+
- For security reasons, only the content of the currently viewed file is served in this special
31689+
live preview mode.
31690+
- HTML files are specifically not served in the live preview of external project files.
31691+
This decision is a precaution against disk file traversal attacks. For example, if a malicious HTML
31692+
file from a user's documents folder were allowed in the live preview, it could potentially upload
31693+
sensitive contents from the appdata folder to a remote server. By restricting the serving of HTML
31694+
files and isolating the external file preview environment, the system enhances security while still
31695+
providing the flexibility to view external files to a limited extend.*/
31696+
function getExternalContent(url) {
31697+
return new Promise((resolve, reject)=>{
31698+
const currentDocument = DocumentManager.getCurrentDocument();
31699+
const currentFile = currentDocument? currentDocument.file : ProjectManager.getSelectedItem();
31700+
url = new URL(url);
31701+
const requestedFileName = path.basename(url.pathname);
31702+
if(currentFile && currentFile.fullPath.endsWith(requestedFileName)) {
31703+
// serve preview
31704+
const fullPath = currentFile.fullPath;
31705+
if(utils.isMarkdownFile(fullPath)) {
31706+
resolve(_getMarkdown(fullPath));
31707+
return;
31708+
}
31709+
if(utils.isHTMLFile(fullPath)) {
31710+
const pageText = _getRedirectionPage(getNoPreviewURL(
31711+
Strings.DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED,
31712+
Strings.DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED_DETAILS));
31713+
resolve({
31714+
path,
31715+
textContents: pageText
31716+
});
31717+
return;
31718+
}
31719+
fs.readFile(fullPath, fs.BYTE_ARRAY_ENCODING, function (error, binContent) {
31720+
if(error){
31721+
resolve({
31722+
path: fullPath,
31723+
is404: true
31724+
});
31725+
return;
31726+
}
31727+
resolve({
31728+
path: fullPath,
31729+
buffer: binContent
31730+
});
31731+
});
31732+
return;
31733+
}
31734+
resolve({
31735+
path: url,
31736+
is404: true
31737+
});
31738+
});
31739+
}
3166831740

3166931741
/**
3167031742
* See BaseServer#start. Starts listenting to StaticServerDomain events.
@@ -31749,6 +31821,14 @@ table tr{background-color:#fff;border-top:1px solid #c6cbd1}table tr:nth-child(2
3174931821
+ `&isLoggingEnabled=${logger.loggingOptions.logLivePreview}`;
3175031822
}
3175131823

31824+
function _getExternalPreviewURL(fullPath) {
31825+
if(utils.isHTMLFile(fullPath)) {
31826+
return getNoPreviewURL(Strings.DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED,
31827+
Strings.DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED_DETAILS);
31828+
}
31829+
return `${staticServerURL}externalProject/${path.basename(fullPath)}`;
31830+
}
31831+
3175231832
function getTabPopoutURL(url) {
3175331833
let openURL = new URL(url);
3175431834
// we tag all externally opened urls with query string parameter phcodeLivePreview="true" to address
@@ -31781,9 +31861,21 @@ table tr{background-color:#fff;border-top:1px solid #c6cbd1}table tr:nth-child(2
3178131861
URL: getNoPreviewURL(),
3178231862
isNoPreview: true
3178331863
});
31864+
return;
3178431865
}
3178531866
const projectRoot = ProjectManager.getProjectRoot().fullPath;
3178631867
let fullPath = currentFile.fullPath;
31868+
if(!ProjectManager.isWithinProject(fullPath)){
31869+
// external project file. Use secure external preview link.
31870+
resolve({
31871+
URL: _getExternalPreviewURL(fullPath),
31872+
filePath: fullPath,
31873+
fullPath: fullPath,
31874+
isMarkdownFile: utils.isMarkdownFile(fullPath),
31875+
isHTMLFile: utils.isHTMLFile(fullPath)
31876+
});
31877+
return;
31878+
}
3178731879
let httpFilePath = null;
3178831880
if(fullPath.startsWith("http://") || fullPath.startsWith("https://")){
3178931881
httpFilePath = fullPath;
@@ -31833,6 +31925,7 @@ table tr{background-color:#fff;border-top:1px solid #c6cbd1}table tr:nth-child(2
3183331925
// node apis
3183431926
exports.tabLoaderOnline = tabLoaderOnline;
3183531927
exports.getContent = getContent;
31928+
exports.getExternalContent = getExternalContent;
3183631929
exports.onLivePreviewMessage = onLivePreviewMessage;
3183731930
exports.PHCODE_LIVE_PREVIEW_QUERY_PARAM = PHCODE_LIVE_PREVIEW_QUERY_PARAM;
3183831931
exports.EVENT_SERVER_READY = EVENT_SERVER_READY;
@@ -32310,9 +32403,11 @@ define("extensionsIntegrated/Phoenix-live-preview/main", function (require, expo
3231032403
// preview breaks sporadically. to alleviate this, we create a new iframe every time.
3231132404
if(!urlPinned) {
3231232405
currentLivePreviewURL = newSrc;
32313-
currentPreviewFile = previewDetails.filePath;
32406+
currentPreviewFile = previewDetails.fullPath;
3231432407
}
32315-
_setTitle(currentPreviewFile);
32408+
let relativeOrFullPath= ProjectManager.makeProjectRelativeIfPossible(currentPreviewFile);
32409+
relativeOrFullPath = Phoenix.app.getDisplayPath(relativeOrFullPath);
32410+
_setTitle(relativeOrFullPath);
3231632411
if(panel.isVisible()) {
3231732412
let newIframe = $(LIVE_PREVIEW_IFRAME_HTML);
3231832413
newIframe.insertAfter($iframe);
@@ -74748,6 +74843,8 @@ define("nls/root/strings", {
7474874843
"DESCRIPTION_LIVEDEV_ENABLE_REVERSE_INSPECT": "false to disable live preview reverse inspect",
7474974844
"DESCRIPTION_LIVEDEV_NO_PREVIEW": "Nothing to preview!",
7475074845
"DESCRIPTION_LIVEDEV_NO_PREVIEW_DETAILS": "Please select an HTML file to preview",
74846+
"DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED": "Preview Unavailable!",
74847+
"DESCRIPTION_LIVEDEV_PREVIEW_RESTRICTED_DETAILS": "This HTML file is not part of the current project. For security reasons, only project files can be live-previewed. To preview this file, open its containing folder as a separate project.",
7475174848
"DESCRIPTION_LIVEDEV_MAIN_HEADING": "Uh Oh! <br>Your current browser doesn't support live preview.",
7475274849
"DESCRIPTION_LIVEDEV_MAIN_SPAN": "Get the best live preview experience by downloading our native apps for Windows, Mac, and Linux from <a href=\"https://phcode.io\" style=\"color: white\">phcode.io</a>.<br>",
7475374850
"DESCRIPTION_LIVEDEV_SECURITY_POPOUT_MESSAGE": "You are about to open a file for live preview. Please proceed only if you trust the source of this project. Click 'Trust Project' to continue, or close this window if you do not trust the source.",

0 commit comments

Comments
 (0)