Skip to content

Commit

Permalink
Merge pull request #17 from wizardAEI/dev
Browse files Browse the repository at this point in the history
Dev
  • Loading branch information
wizardAEI authored Dec 29, 2023
2 parents 3aaa087 + e1cc65a commit 7678945
Show file tree
Hide file tree
Showing 18 changed files with 493 additions and 256 deletions.
8 changes: 5 additions & 3 deletions dev-app-update.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
provider: generic
url: https://example.com/auto-updates
updaterCacheDirName: Gomoon-updater
provider: github
owner: wizardAEI
repo: Gomoon
# url: https://example.com/auto-updates
# updaterCacheDirName: Gomoon-updater
2 changes: 2 additions & 0 deletions electron-builder.yml
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@ nsis:
shortcutName: ${productName}
uninstallDisplayName: ${productName}
createDesktopShortcut: always
allowToChangeInstallationDirectory: true
language: 2052 # 简体中文
mac:
extendInfo:
- NSCameraUsageDescription: Application requests access to the device's camera.
Expand Down
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "gomoon",
"productName": "Gomoon",
"version": "1.0.3",
"version": "1.0.5",
"description": "A ai tools for everyone on Mac, Windows and Linux.",
"main": "./out/main/index.js",
"author": "aei",
Expand Down Expand Up @@ -52,6 +52,7 @@
"solidjs-use": "^2.3.0",
"tesseract.js": "^5.0.3",
"ulid": "^2.3.0",
"vectordb": "^0.4.1",
"xlsx": "^0.18.5"
},
"devDependencies": {
Expand Down
24 changes: 17 additions & 7 deletions src/main/eventHandler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,13 @@ import {
SettingModel,
UserDataModel
} from './model/model'
import { hideWindow, minimize, setQuicklyWakeUp, updateCSP, updateCors } from './window'
import {
hideWindow,
minimize,
setQuicklyWakeUp,
updateRespHeaders,
updateSendHeaders
} from './window'
import parseFile from './lib/ai/fileLoader'
import { writeFile } from 'fs'
import { parseURL2Str } from './lib/ai/parseURL'
Expand All @@ -43,9 +49,11 @@ export function initAppEventsHandler() {
urls.push(config.models.OpenAI.baseURL)
}
if (urls.toString() !== preBaseUrls.toString()) {
updateCors(urls)
updateCSP({
'connect-src': urls
updateSendHeaders(urls)
updateRespHeaders(urls, {
cspItems: {
'connect-src': urls
}
})
preBaseUrls = urls
}
Expand All @@ -63,9 +71,11 @@ export function initAppEventsHandler() {
urls.push(models.OpenAI.baseURL)
}
if (urls.toString() !== preBaseUrls.toString()) {
updateCors(urls)
updateCSP({
'connect-src': urls
updateSendHeaders(urls)
updateRespHeaders(urls, {
cspItems: {
'connect-src': urls
}
})
preBaseUrls = urls
}
Expand Down
9 changes: 4 additions & 5 deletions src/main/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,20 +10,19 @@ app.dock?.setIcon(icon)
app.dock?.setMenu(Menu.buildFromTemplate([]))

// 检测只启动一个app
const gotTheLock = app.requestSingleInstanceLock();
const gotTheLock = app.requestSingleInstanceLock()

if (!gotTheLock) {
// 如果获取锁失败,说明已经有一个实例在运行了,可以直接退出
app.quit();
app.quit()
} else {
app.on('second-instance', () => {
// 当运行第二个实例时,将会聚焦到 myWindow 这个窗口
showWindow();
});
showWindow()
})
}

app.whenReady().then(() => {

// Set app user model id for windows
electronApp.setAppUserModelId('com.electron')

Expand Down
47 changes: 0 additions & 47 deletions src/main/test.ts

This file was deleted.

128 changes: 68 additions & 60 deletions src/main/window.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,8 @@ import {
clipboard,
globalShortcut,
OnBeforeSendHeadersListenerDetails,
BeforeSendResponse
BeforeSendResponse,
session
} from 'electron'
import { join } from 'path'
import { is } from '@electron-toolkit/utils'
Expand All @@ -16,6 +17,39 @@ import trayIcon from '../../resources/[email protected]?asset'
import { loadUserConfig } from './model'
import { getResourcesPath, quitApp } from './lib'
import { spawn } from 'child_process'
import { autoUpdater } from 'electron-updater'

let mainWindow: BrowserWindow | null = null
let tray: Tray | null = null
let preKeys = ''

export function setQuicklyWakeUp(keys: string) {
/**
* FEAT: 按键监听
*/
globalShortcut.register(keys, () => {
if (mainWindow?.isVisible()) {
mainWindow?.hide()
return
}
mainWindow?.webContents.send('show-window')
mainWindow?.show()
})
preKeys && globalShortcut.unregister(preKeys)
preKeys = keys
}

export function hideWindow() {
mainWindow?.hide()
}

export function minimize() {
mainWindow?.minimize()
}

export function showWindow() {
mainWindow?.show()
}

const cors: {
defaultURLs: string[]
Expand All @@ -36,7 +70,7 @@ const cors: {
const { origin, host } = new URL(details.url)
details.requestHeaders['Origin'] = origin
details.requestHeaders['Host'] = host
callback({ requestHeaders: details.requestHeaders })
callback({ cancel: false, requestHeaders: details.requestHeaders })
}
}
type cspItem = 'default-src' | 'script-src' | 'style-src' | 'connect-src' | 'img-src' | 'worker-src'
Expand All @@ -50,11 +84,12 @@ function csp(items?: {
'script-src': ['https://cdn.jsdelivr.net', "'unsafe-eval'"],
'style-src': ["'unsafe-inline'"],
'connect-src': [
'https://dashscope.aliyuncs.com',
'https://api.openai.com',
'https://tiktoken.pages.dev',
'https://aip.baidubce.com',
'https://cdn.jsdelivr.net',
// 'https://dashscope.aliyuncs.com',
// 'https://api.openai.com',
// 'https://tiktoken.pages.dev',
// 'https://aip.baidubce.com',
// 'https://cdn.jsdelivr.net',
'https:',
'http://www.baidu.com',
'data:'
],
Expand All @@ -66,6 +101,16 @@ function csp(items?: {
if (!item) {
return ''
}
// 去除网址后的路径
item = item.map((url) => {
try {
const { origin } = new URL(url)
if (origin === 'null') return url
return origin || url
} catch (e) {
return url
}
})
return item.join(' ')
}
for (let item in defaultItem) {
Expand All @@ -78,74 +123,33 @@ function csp(items?: {
'; '
}
return cspStr
// "default-src 'self'; script-src https://cdn.jsdelivr.net 'self' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; connect-src 'self' https://dashscope.aliyuncs.com https://api.openai.com https://api.chatanywhere.com.cn https://api.chatanywhere.tech https://tiktoken.pages.dev https://aip.baidubce.com https://cdn.jsdelivr.net http://www.baidu.com data:; img-src https: http: data: 'self'; worker-src 'self' blob:;"
}

let mainWindow: BrowserWindow | null = null
let tray: Tray | null = null
let preKeys = ''

export function setQuicklyWakeUp(keys: string) {
/**
* FEAT: 按键监听
*/
globalShortcut.register(keys, () => {
if (mainWindow?.isVisible()) {
mainWindow?.hide()
return
}
mainWindow?.webContents.send('show-window')
mainWindow?.show()
})
preKeys && globalShortcut.unregister(preKeys)
preKeys = keys
}

export function hideWindow() {
mainWindow?.hide()
}

export function minimize() {
mainWindow?.minimize()
}

export function showWindow() {
mainWindow?.show()
}

export function updateCors(urls: string[]) {
mainWindow?.webContents.session.clearCache()
mainWindow?.webContents.session.webRequest.onBeforeSendHeaders(
export function updateSendHeaders(urls: string[] = []) {
session.defaultSession.webRequest.onBeforeSendHeaders(
{ urls: cors.defaultURLs.concat(urls.map((url) => (url.endsWith('/*') ? url : url + '/*'))) },
cors.handler
)
mainWindow?.webContents.session.webRequest.onHeadersReceived(
}
export function updateRespHeaders(
urls: string[] = [],
conf?: { cspItems?: { [key in cspItem]?: string[] } }
) {
session.defaultSession.webRequest.onHeadersReceived(
{ urls: cors.defaultURLs.concat(urls.map((url) => (url.endsWith('/*') ? url : url + '/*'))) },
(details, callback) => {
if (details.responseHeaders) {
details.responseHeaders['Access-Control-Allow-Origin'] = []
details.responseHeaders['access-control-allow-origin'] = ['*']
details.responseHeaders['access-control-allow-headers'] = ['*']
details.responseHeaders['access-control-allow-methods'] = ['*']
details.responseHeaders['access-control-allow-credentials'] = ['true']
details.responseHeaders['Content-Security-Policy'] = [csp(conf?.cspItems)]
}
callback({ responseHeaders: details.responseHeaders })
}
)
}

export function updateCSP(items: { [key in cspItem]?: string[] }) {
mainWindow?.webContents.session.clearCache()
mainWindow?.webContents.session.webRequest.onHeadersReceived((details, callback) => {
callback({
responseHeaders: {
...details.responseHeaders,
'Content-Security-Policy': csp(items)
}
})
})
}

export function createWindow(): void {
const userConfig = loadUserConfig()

Expand All @@ -167,6 +171,8 @@ export function createWindow(): void {
// preConfig
mainWindow!.setAlwaysOnTop(userConfig.isOnTop, 'status')

autoUpdater.checkForUpdatesAndNotify()

// FEAT: 链接跳转,自动打开浏览器
mainWindow.webContents.on('will-frame-navigate', (event) => {
if (event.url.includes('localhost')) {
Expand All @@ -179,11 +185,10 @@ export function createWindow(): void {
// FEAT: 双击复制回答
if (userConfig.canMultiCopy) {
let filename = 'eventTracker'
if (process.arch === 'x64') {
filename = 'eventTracker_x64'
}
if (process.platform === 'win32') {
filename += '.exe'
} else if (process.arch === 'x64') {
filename = 'eventTracker_x64'
}
const eventTracker = spawn(getResourcesPath(filename))
eventTracker.stdout.on('data', (data) => {
Expand Down Expand Up @@ -245,6 +250,9 @@ export function createWindow(): void {
return { action: 'deny' }
})

updateSendHeaders()
updateRespHeaders()

// HMR for renderer base on electron-vite cli.
// Load the remote URL for development or the local html file for production.
if (is.dev && process.env['ELECTRON_RENDERER_URL']) {
Expand Down
Binary file added src/renderer/public/groupcode.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 1 addition & 1 deletion src/renderer/src/components/Message/Md.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ export default function (props: { class: string; content: string }) {
token.content
)} class="cursor-pointer absolute top-1 right-1 z-10 hover:h-3 group/copy copy-btn">
<svg xmlns="http://www.w3.org/2000/svg" width="1em" height="1em" viewBox="0 0 32 32"><path fill="currentColor" d="M28 10v18H10V10h18m0-2H10a2 2 0 0 0-2 2v18a2 2 0 0 0 2 2h18a2 2 0 0 0 2-2V10a2 2 0 0 0-2-2Z" /><path fill="currentColor" d="M4 18H2V4a2 2 0 0 1 2-2h14v2H4Z" /></svg>
<div class="absolute -right-1 top-3 opacity-0 group-hover/copy:opacity-100 duration-300 text-text1">
<div class="absolute select-none -right-1 top-3 opacity-0 group-hover/copy:opacity-100 duration-300 text-text1">
${copied() ? 'Copied' : 'Copy'}
</div>
</div>
Expand Down
Loading

0 comments on commit 7678945

Please sign in to comment.