Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

open explorer alpha on start #976

Merged
merged 17 commits into from
Aug 7, 2024
Merged
14 changes: 7 additions & 7 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
"bugs": "https://github.com/decentraland/js-sdk-toolchain/issues",
"dependencies": {
"@actions/core": "^1.10.0",
"@dcl/protocol": "1.0.0-9959547690.commit-67e81c4",
"@dcl/protocol": "1.0.0-10043247792.commit-428d1eb",
"@dcl/quickjs-emscripten": "^0.21.0-3680274614.commit-1808aa1",
"@dcl/ts-proto": "1.153.0",
"@types/fs-extra": "^9.0.12",
Expand Down
14 changes: 7 additions & 7 deletions packages/@dcl/sdk-commands/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion packages/@dcl/sdk-commands/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
"@dcl/inspector": "file:../inspector",
"@dcl/linker-dapp": "^0.12.0",
"@dcl/mini-comms": "1.0.1-20230216163137.commit-a4c75be",
"@dcl/protocol": "1.0.0-9959547690.commit-67e81c4",
"@dcl/protocol": "1.0.0-10043247792.commit-428d1eb",
"@dcl/quests-client": "^1.0.3",
"@dcl/quests-manager": "^0.1.4",
"@dcl/rpc": "^1.1.1",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ export async function createDataLayer(components: Pick<CliComponents, 'fs' | 'lo
fs,
engine: dataLayerHost.engine
}

const rpcServer = createRpcServer<DataLayerContext>({ logger: components.logger })

rpcServer.setHandler(async function rpcHandler(serverPort: RpcServerPort<DataLayerContext>) {
Expand Down
33 changes: 33 additions & 0 deletions packages/@dcl/sdk-commands/src/commands/start/explorer-alpha.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { CliComponents } from '../../components'

const isWindows = /^win/.test(process.platform)

export async function runExplorerAlpha(
components: CliComponents,
opts: { cwd: string; realm: string; baseCoords: { x: number; y: number } }
) {
const { cwd, realm, baseCoords } = opts

if (await runApp(components, { cwd, realm, baseCoords })) {
return
}

components.logger.log('Please download & install the Decentraland Desktop Client: https://dcl.gg/explorer\n\n')
}

async function runApp(
components: CliComponents,
{ cwd, realm, baseCoords }: { cwd: string; realm: string; baseCoords: { x: number; y: number } }
) {
const cmd = isWindows ? 'start' : 'open'
try {
const params = `realm=${realm}&position=${baseCoords.x},${baseCoords.y}&local-scene=true`
const app = `decentraland://"${params}"`
await components.spawner.exec(cwd, cmd, [app], { silent: true })
components.logger.info(`Desktop client: decentraland://${params}\n`)
return true
} catch (e: any) {
components.logger.error('Decentraland Desktop Client failed with: ', e.message)
return false
}
}
30 changes: 22 additions & 8 deletions packages/@dcl/sdk-commands/src/commands/start/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ import { getValidWorkspace } from '../../logic/workspace-validations'
import { printCurrentProjectStarting, printProgressInfo, printWarning } from '../../logic/beautiful-logs'
import { Result } from 'arg'
import { startValidations } from '../../logic/project-validations'
import { runExplorerAlpha } from './explorer-alpha'

interface Options {
args: Result<typeof args>
Expand All @@ -49,7 +50,8 @@ export const args = declareArgs({
'-w': '--no-watch',
'--skip-build': Boolean,
'--desktop-client': Boolean,
'--data-layer': Boolean
'--data-layer': Boolean,
'--explorer-alpha': Boolean
})

export async function help(options: Options) {
Expand Down Expand Up @@ -90,6 +92,7 @@ export async function main(options: Options) {
const watch = !options.args['--no-watch']
const withDataLayer = options.args['--data-layer']
const enableWeb3 = options.args['--web3']
const explorerAlpha = options.args['--explorer-alpha']

let hasSmartWearable = false

Expand Down Expand Up @@ -135,7 +138,7 @@ export async function main(options: Options) {
})
const logs = await createConsoleLogComponent({})
const ws = await createWsComponent({ logs })
const server = await createServerComponent<PreviewComponents>({ config, logs, ws: ws.ws }, { cors: {} })
const server = await createServerComponent<PreviewComponents>({ config, ws: ws.ws, logs }, { cors: {} })
const rooms = await createRoomsComponent({
metrics,
logs,
Expand Down Expand Up @@ -170,7 +173,7 @@ export async function main(options: Options) {
await wireRouter(components, workspace, dataLayer)
if (watch) {
for (const project of workspace.projects) {
await wireFileWatcherToWebSockets(components, project.workingDirectory, project.kind)
await wireFileWatcherToWebSockets(components, project.workingDirectory, project.kind, !!explorerAlpha)
}
}
await startComponents()
Expand All @@ -179,7 +182,9 @@ export async function main(options: Options) {
const availableURLs: string[] = []

printProgressInfo(options.components.logger, 'Preview server is now running!')
components.logger.log('Available on:\n')
if (!explorerAlpha) {
components.logger.log('Available on:\n')
}

Object.keys(networkInterfaces).forEach((dev) => {
;(networkInterfaces[dev] || []).forEach((details) => {
Expand All @@ -203,8 +208,10 @@ export async function main(options: Options) {
return a.toLowerCase().includes('localhost') || a.includes('127.0.0.1') || a.includes('0.0.0.0') ? -1 : 1
})

for (const addr of sortedURLs) {
components.logger.log(` ${addr}`)
if (!explorerAlpha) {
for (const addr of sortedURLs) {
components.logger.log(` ${addr}`)
}
}

if (options.args['--desktop-client']) {
Expand All @@ -216,11 +223,18 @@ export async function main(options: Options) {
}
}

components.logger.log('\n Details:\n')
if (!explorerAlpha) {
components.logger.log('\n Details:\n')
}
components.logger.log('\nPress CTRL+C to exit\n')

if (explorerAlpha) {
const realm = new URL(sortedURLs[0]).origin
await runExplorerAlpha(components, { cwd: workingDirectory, realm, baseCoords })
}

// Open preferably localhost/127.0.0.1
if (openBrowser && sortedURLs.length && !options.args['--desktop-client']) {
if (!explorerAlpha && openBrowser && sortedURLs.length && !options.args['--desktop-client']) {
try {
await open(sortedURLs[0])
} catch (_) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ import { PreviewComponents } from '../types'
import { sceneUpdateClients } from './routes'
import { ProjectUnion } from '../../../logic/project-validations'
import { b64HashingFunction } from '../../../logic/project-files'
import {
WsSceneMessage,
UpdateModelType
} from '@dcl/protocol/out-js/decentraland/sdk/development/local_development.gen'

function debounce<T extends (...args: any[]) => void>(callback: T, delay: number) {
let debounceTimer: NodeJS.Timeout
Expand All @@ -24,38 +28,91 @@ function debounce<T extends (...args: any[]) => void>(callback: T, delay: number
export async function wireFileWatcherToWebSockets(
components: Pick<PreviewComponents, 'fs' | 'ws'>,
projectRoot: string,
projectKind: ProjectUnion['kind']
projectKind: ProjectUnion['kind'],
desktopClient: boolean
) {
const ignored = await getDCLIgnorePatterns(components, projectRoot)

const sceneId = b64HashingFunction(projectRoot)
chokidar
.watch(path.resolve(projectRoot), {
atomic: false,
ignored,
ignoreInitial: false,
cwd: projectRoot
})
.on('unlink', (_: unknown, file: string) => {
if (desktopClient) {
return removeModel(sceneId, file)
}
})
.on(
'all',
debounce(async (_, _file) => {
// TODO: accumulate changes in an array and debounce
return updateScene(projectRoot, sceneUpdateClients, projectKind)
debounce(async (a, file) => {
if (desktopClient) {
updateScene(sceneId, file)
}
return __LEGACY__updateScene(projectRoot, sceneUpdateClients, projectKind)
}, 500)
)
}

/*
* IMPORTANT: this is a legacy protocol and needs to be revisited for SDK7
function isGLTFModel(file: string) {
if (!file) return false
return file.toLowerCase().endsWith('.glb') || file.toLowerCase().endsWith('.gltf')
}

function updateScene(sceneId: string, file: string) {
let message: WsSceneMessage['message']
if (isGLTFModel(file)) {
message = {
$case: 'updateModel',
updateModel: { hash: b64HashingFunction(file), sceneId, src: file, type: UpdateModelType.UMT_CHANGE }
}
} else {
message = {
$case: 'updateScene',
updateScene: { sceneId }
}
}
sendSceneMessage({ message })
}

function removeModel(sceneId: string, file: string) {
if (isGLTFModel(file)) {
const sceneMessage: WsSceneMessage = {
message: {
$case: 'updateModel',
updateModel: { sceneId, src: file, hash: b64HashingFunction(file), type: UpdateModelType.UMT_REMOVE }
}
}

sendSceneMessage(sceneMessage)
}
}

function sendSceneMessage(sceneMessage: WsSceneMessage) {
const message = WsSceneMessage.encode(sceneMessage).finish()
for (const client of sceneUpdateClients) {
if (client.readyState === WebSocket.OPEN) {
client.send(message, { binary: true })
}
}
}

/**
* @deprecated old explorer (kernel)
*/
function updateScene(dir: string, clients: Set<WebSocket>, projectKind: ProjectUnion['kind']): void {
export function __LEGACY__updateScene(dir: string, clients: Set<WebSocket>, projectKind: ProjectUnion['kind']): void {
for (const client of clients) {
if (client.readyState === WebSocket.OPEN) {
const message: sdk.SceneUpdate = {
type: sdk.SCENE_UPDATE,
payload: { sceneId: b64HashingFunction(dir), sceneType: projectKind }
}

client.send(sdk.UPDATE)
client.send(JSON.stringify(message))
// Old explorer
client.send(sdk.UPDATE, { binary: false })
client.send(JSON.stringify(message), { binary: false })
}
}
}
1 change: 0 additions & 1 deletion packages/@dcl/sdk-commands/src/commands/start/server/ws.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ export type WebSocketComponent = IBaseComponent & {
*/
export async function createWsComponent(_: Pick<PreviewComponents, 'logs'>): Promise<WebSocketComponent> {
const ws = new WebSocketServer({ noServer: true })

async function stop() {
ws.close()
}
Expand Down
1 change: 0 additions & 1 deletion packages/@dcl/sdk-commands/src/logic/bundle.ts
Original file line number Diff line number Diff line change
Expand Up @@ -291,7 +291,6 @@ function compositeLoader(components: BundleComponents, options: SingleProjectOpt
'Some composites are not included because of errors while compiling them. There can be unexpected behavior in the scene, check the errors and try to fix them.'
)
} else if (!lastBuiltSuccessful) {
components.logger.log('Composites built without errors.')
}
lastBuiltSuccessful = !data.withErrors
}
Expand Down
Loading