Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
energye
energy
提交
2b5854b4
energy
项目概览
energye
/
energy
通知
13
Star
2
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
energy
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
2b5854b4
编写于
8月 24, 2023
作者:
yanghye
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
添加 本地和内置方式直接加载资源
上级
62b10d42
变更
2
隐藏空白更改
内联
并排
Showing
2 changed file
with
56 addition
and
35 deletion
+56
-35
cef/local-load-resource.go
cef/local-load-resource.go
+35
-14
consts/consts.go
consts/consts.go
+21
-21
未找到文件。
cef/local-load-resource.go
浏览文件 @
2b5854b4
...
...
@@ -12,7 +12,6 @@ package cef
import
(
"embed"
"fmt"
"github.com/energye/energy/v2/consts"
"github.com/energye/energy/v2/logger"
"io/ioutil"
...
...
@@ -28,7 +27,7 @@ const (
sff
=
"://"
)
// LocalCustomerScheme 本地资源加载自定义协议
// LocalCustomerScheme 本地资源加载自定义
固定
协议
// file, fs
type
LocalCustomerScheme
string
...
...
@@ -97,12 +96,14 @@ func (m *LocalLoadResource) SetFS(v *embed.FS) {
// SetEnableCache
// 设置是否启用本地资源缓存到内存, 默认false: 未启用
// 开启该配置会占用内存
func
(
m
*
LocalLoadResource
)
SetEnableCache
(
v
bool
)
{
m
.
enableCache
=
v
}
// SetEnable
// 设置是否启用本地资源加载, 默认false: 未启用
// 提示: 启用该功能, 目前无法加载本地媒体, 媒体资源可http方式加载
func
(
m
*
LocalLoadResource
)
SetEnable
(
v
bool
)
{
m
.
enable
=
v
}
...
...
@@ -120,7 +121,7 @@ func (m *LocalLoadResource) SetDomain(domain string) {
// SetScheme
// 设置本地资源加载自定义协议
func
(
m
*
LocalLoadResource
)
SetScheme
(
scheme
LocalCustomerScheme
)
{
if
scheme
==
""
{
if
scheme
==
""
||
(
scheme
!=
LocalCSFS
&&
scheme
!=
LocalCSFile
)
{
m
.
scheme
=
LocalCSFS
return
}
...
...
@@ -139,6 +140,7 @@ func (m *LocalLoadResource) getMimeType(extension string) string {
}
}
// return xxx.js = js, xxx.html = html
func
(
m
*
LocalLoadResource
)
ext
(
path
string
)
string
{
for
i
:=
len
(
path
)
-
1
;
i
>=
0
&&
!
os
.
IsPathSeparator
(
path
[
i
]);
i
--
{
if
path
[
i
]
==
'.'
{
...
...
@@ -148,48 +150,54 @@ func (m *LocalLoadResource) ext(path string) string {
return
""
}
// 使用本地资源加载时,先验证每个请求的合法性
// 所支持的scheme, domain
// URL格式, fs://energy/index.html, 文件路径必须包含扩展名
func
(
m
*
LocalLoadResource
)
checkRequest
(
request
*
ICefRequest
)
(
*
source
,
bool
)
{
rt
:=
request
.
ResourceType
()
// 根据资源类型跳过哪些资源不被本地加载
// TODO: rt_media 类型应该在此去除
switch
rt
{
case
consts
.
RT_XHR
:
case
consts
.
RT_XHR
,
consts
.
RT_MEDIA
,
consts
.
RT_PING
,
consts
.
RT_CSP_REPORT
,
consts
.
RT_PLUGIN_RESOURCE
:
return
nil
,
false
}
url
:=
request
.
URL
()
logger
.
Debug
(
"URL:"
,
url
)
logger
.
Debug
(
"URL:"
,
url
,
rt
)
idx
:=
strings
.
Index
(
url
,
":"
)
if
idx
!=
-
1
{
scheme
:=
url
[
:
idx
]
if
scheme
!=
string
(
m
.
scheme
)
{
logger
.
Error
(
"Local load resource, scheme invalid should:"
,
LocalCSFS
,
"or"
,
LocalCSFile
,
"source url:"
,
url
)
logger
.
Error
(
"Local load resource, scheme invalid should:"
,
LocalCSFS
,
"or"
,
LocalCSFile
)
return
nil
,
false
}
idx
=
strings
.
Index
(
url
,
"://"
)
if
idx
==
-
1
{
logger
.
Error
(
"Incorrect protocol domain address should: [fs | file]://energy/index.html"
,
"source url:"
,
url
)
logger
.
Error
(
"Incorrect protocol domain address should: [fs | file]://energy/index.html"
)
return
nil
,
false
}
domainPath
:=
url
[
idx
+
3
:
]
idx
=
strings
.
Index
(
domainPath
,
"/"
)
if
idx
==
-
1
{
logger
.
Error
(
"Incorrect protocol domain path should: [fs | file]://energy/index.html"
,
"source url:"
,
url
)
logger
.
Error
(
"Incorrect protocol domain path should: [fs | file]://energy/index.html"
)
return
nil
,
false
}
domain
:=
domainPath
[
:
idx
]
if
domain
!=
m
.
domain
{
logger
.
Error
(
"Incorrect protocol domain should: [fs | file]://energy/index.html"
,
"source url:"
,
url
)
logger
.
Error
(
"Incorrect protocol domain should: [fs | file]://energy/index.html"
)
return
nil
,
false
}
idx
=
strings
.
Index
(
domainPath
,
"/"
)
if
idx
==
-
1
{
logger
.
Error
(
"Incorrect protocol path should: [fs | file]://energy/index.html"
,
"source url:"
,
url
)
logger
.
Error
(
"Incorrect protocol path should: [fs | file]://energy/index.html"
)
return
nil
,
false
}
path
:=
domainPath
[
idx
:
]
ext
:=
m
.
ext
(
path
)
if
ext
==
""
{
logger
.
Error
(
"Incorrect resources should: file.[ext](MimeType)"
,
"source url:"
,
url
)
logger
.
Error
(
"Incorrect resources should: file.[ext](MimeType)"
)
return
nil
,
false
}
// 如果开启缓存,直接在缓存拿指定地址的source
if
m
.
enableCache
{
if
s
,
ok
:=
m
.
sourceCache
[
path
];
ok
{
return
s
,
true
...
...
@@ -204,9 +212,12 @@ func (m *LocalLoadResource) checkRequest(request *ICefRequest) (*source, bool) {
return
nil
,
false
}
// 读取文件
func
(
m
*
source
)
readFile
()
bool
{
// 必须设置文件根目录, scheme是file时, fileRoot为本地文件目录, scheme是fs时, fileRoot为fs的目录名
if
localLoadResource
.
fileRoot
!=
""
{
if
localLoadResource
.
scheme
==
LocalCSFile
{
// 在本地读取
data
,
err
:=
ioutil
.
ReadFile
(
filepath
.
Join
(
localLoadResource
.
fileRoot
,
m
.
path
))
if
err
==
nil
{
m
.
bytes
=
data
...
...
@@ -214,6 +225,7 @@ func (m *source) readFile() bool {
}
logger
.
Error
(
"ReadFile:"
,
err
.
Error
())
}
else
if
localLoadResource
.
scheme
==
LocalCSFS
{
//在fs读取
data
,
err
:=
localLoadResource
.
fs
.
ReadFile
(
localLoadResource
.
fileRoot
+
m
.
path
)
if
err
==
nil
{
m
.
bytes
=
data
...
...
@@ -222,13 +234,17 @@ func (m *source) readFile() bool {
logger
.
Error
(
"ReadFile:"
,
err
.
Error
())
}
}
//失败时,返回404,文件不存在
return
false
}
// 打开资源
func
(
m
*
source
)
open
(
request
*
ICefRequest
,
callback
*
ICefCallback
)
(
handleRequest
,
result
bool
)
{
m
.
readPosition
=
0
// 当前资源的响应设置默认值
m
.
status
=
404
m
.
statusText
=
"Not Found"
// 如果开启缓存,直接在缓存取
if
localLoadResource
.
enableCache
{
if
m
.
bytes
==
nil
{
if
!
m
.
readFile
()
{
...
...
@@ -246,12 +262,12 @@ func (m *source) open(request *ICefRequest, callback *ICefCallback) (handleReque
m
.
status
=
200
m
.
statusText
=
"OK"
}
logger
.
Debug
(
"open success"
,
m
.
path
)
callback
.
Cont
(
)
return
true
,
true
}
// 设置响应信息
func
(
m
*
source
)
response
(
response
*
ICefResponse
)
(
responseLength
int64
,
redirectUrl
string
)
{
fmt
.
Println
(
"response"
)
response
.
SetStatus
(
m
.
status
)
response
.
SetStatusText
(
m
.
statusText
)
response
.
SetMimeType
(
m
.
mimeType
)
...
...
@@ -259,8 +275,8 @@ func (m *source) response(response *ICefResponse) (responseLength int64, redirec
return
}
// 读取bytes, 返回到dataOut
func
(
m
*
source
)
read
(
dataOut
uintptr
,
bytesToRead
int32
,
callback
*
ICefResourceReadCallback
)
(
bytesRead
int32
,
result
bool
)
{
fmt
.
Println
(
"read"
,
dataOut
,
bytesToRead
)
if
m
.
bytes
!=
nil
&&
len
(
m
.
bytes
)
>
0
{
var
i
int32
=
0
// 默认 0
for
i
<
bytesToRead
&&
m
.
readPosition
<
len
(
m
.
bytes
)
{
...
...
@@ -268,6 +284,11 @@ func (m *source) read(dataOut uintptr, bytesToRead int32, callback *ICefResource
m
.
readPosition
++
i
++
}
// 读取到最后不缓存时,清空
if
i
==
0
&&
!
localLoadResource
.
enableCache
{
m
.
bytes
=
nil
}
callback
.
Cont
(
int64
(
i
))
return
i
,
i
>
0
}
return
...
...
consts/consts.go
浏览文件 @
2b5854b4
...
...
@@ -410,27 +410,27 @@ type TCefErrorCode = types.Int32
type
TCefResourceType
=
types
.
Int32
const
(
RT_MAIN_FRAME
=
TCefResourceType
(
iota
)
RT_SUB_FRAME
RT_STYLESHEET
RT_SCRIPT
RT_IMAGE
RT_FONT_RESOURCE
RT_SUB_RESOURCE
RT_OBJECT
RT_MEDIA
RT_WORKER
RT_SHARED_WORKER
RT_PREFETCH
RT_FAVICON
RT_XHR
RT_PING
RT_SERVICE_WORKER
RT_CSP_REPORT
RT_PLUGIN_RESOURCE
RT_EMPTY_FILLER_TYPE_DO_NOT_USE
// This type doesn't exist in CEF and it's here just to fill this position.
RT_NAVIGATION_PRELOAD_MAIN_FRAME
//
This type must have a value of 19
RT_NAVIGATION_PRELOAD_SUB_FRAME
RT_MAIN_FRAME
=
TCefResourceType
(
iota
)
// Top level page.
RT_SUB_FRAME
// Frame or iframe.
RT_STYLESHEET
// CSS stylesheet.
RT_SCRIPT
// External script.
RT_IMAGE
// Image (jpg/gif/png/etc).
RT_FONT_RESOURCE
// Font.
RT_SUB_RESOURCE
// Some other subresource. This is the default type if the actual type is unknown
RT_OBJECT
// Object (or embed) tag for a plugin, or a resource that a plugin requested.
RT_MEDIA
// Media resource.
RT_WORKER
// Main resource of a dedicated worker.
RT_SHARED_WORKER
// Main resource of a shared worker.
RT_PREFETCH
// Explicitly requested prefetch.
RT_FAVICON
// Favicon
RT_XHR
// XMLHttpRequest
RT_PING
// A request for a "<ping>".
RT_SERVICE_WORKER
// Main resource of a service worker.
RT_CSP_REPORT
// A report of Content Security Policy violations.
RT_PLUGIN_RESOURCE
// A resource that a plugin requested.
RT_EMPTY_FILLER_TYPE_DO_NOT_USE
// This type doesn't exist in CEF and it's here just to fill this position.
RT_NAVIGATION_PRELOAD_MAIN_FRAME
// A main-frame service worker navigation preload request.
This type must have a value of 19
RT_NAVIGATION_PRELOAD_SUB_FRAME
// A sub-frame service worker navigation preload request.
)
// /include/internal/cef_types.h (cef_transition_type_t)
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录