什么才是开发油猴脚本最好的体验 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
爱意满满的作品展示区。
lisongeee
V2EX    分享创造

什么才是开发油猴脚本最好的体验

  •  
  •   lisongeee
    lisonge 2022-05-09 11:05:25 +08:00 5676 次点击
    这是一个创建于 1321 天前的主题,其中的信息可能已经有所发展或是发生改变。
    我发现现有的辅助油猴脚本开发的体验都一言难尽

    比如需要手动配置 UserScript ,我为什么不能自动配置自动在浏览器打开呢,配置更改的时候也自动在浏览器打开

    还有 @require 的配置,我为什么不能在插件里配置库的 cdn 链接,然后自动注入 UserScript 。而且这个是随打包的版本确定的,不是静态的

    还有开发时热重载的体验,我想要类似开发 vue/react 项目的正常体验,大多数操作只需要局部刷新,不需要刷新宿主页面

    因此为了实现这些良好的体验,我开发了一个 vite 插件

    https://github.com/lisonge/vite-plugin-monkey/blob/main/README_zh.md

    得益于 vite 明确区分了 server 和 build 的良好架构,

    只要稍做配置,你甚至能将现有的 vue/react 项目直接转成 油猴脚本

    当然有什么用的不舒适的地方可以直接指出
    52 条回复    2023-05-23 12:58:21 +08:00
    statumer
        1
    statumer  
       2022-05-09 11:43:54 +08:00 via iPhone
    看着很棒啊
    lisongeee
        2
    lisongeee  
    OP
       2022-05-09 11:47:34 +08:00
    @statumer
    哈哈谢谢,有空可以用一下,最近在 mo,想改进一下这个插件,奈何用的人比较少
    golangLover
        3
    golangLover  
       2022-05-09 12:34:55 +08:00
    你这 TS definition 写的好仔细啊。赞一个
    yunser
        4
    yunser  
       2022-05-09 12:56:27 +08:00
    刚好最近想要写一个 UserScript ,试用了一下。体验非常好,以后就用这个了。
    lyxeno
        5
    lyxeno  
       2022-05-09 13:33:41 +08:00
    已 star,有空试用一下
    jawilx
        6
    jawilx  
       2022-05-09 13:53:40 +08:00
    虽然没开发过油猴脚本,但是这个项目看着很不错,以后学习下
    Johnming
        7
    Johnming  
       2022-05-10 11:09:05 +08:00
    感觉很棒,可以试试
    lisongeee
        8
    lisongeee  
    OP
       2022-05-12 11:39:46 +08:00
    更新了一下,优化了一些问题
    lisongeee
        9
    lisongeee  
    OP
       2022-08-05 10:49:23 +08:00
    更新了一下,又优化了一些问题,目前正在完善 GM_api 的类型注释和 让其支持 esm 引入

    <https://github.com/lisonge/vite-plugin-monkey>
    lisongeee
        10
    lisongeee  
    OP
       2022-08-10 11:30:17 +08:00
    更新:现在支持使用 esm 使用 GM_api
    lisongeee
        14
    lisongeee  
    OP
       2022-08-18 17:09:54 +08:00
    lisongeee
        15
    lisongeee  
    OP
       2022-08-18 17:14:51 +08:00
    lisongeee
        16
    lisongeee  
    OP
       2022-08-18 17:32:11 +08:00
    # vite-plugin-monkey

    <p>
    <a href="https://www.npmjs.com/package/vite-plugin-monkey"><img src="https://img.shields.io/npm/v/vite-plugin-monkey.svg" alt="npm package"></a>
    <a href="https://github.com/lisonge/vite-plugin-monkey/releases/"><img src="https://img.shields.io/node/v/vite-plugin-monkey.svg" alt="node compatibility"></a>
    </p>

    [README](README.md) | [中文文档](README_zh.md)

    vite plugin server and build \*.user.js for [Tampermonkey]( https://www.tampermonkey.net/) and [Violentmonkey]( https://violentmonkey.github.io/) and [Greasemonkey]( https://www.greasespot.net/)

    ## feature

    - support Tampermonkey and Violentmonkey and Greasemonkey
    - inject userscript comment to build bundle
    - auto open \*.user.js in default browser when userscript change
    - external cdn url inject to userscript @require
    - use GM_api by ESM import with type hints
    - when vite preview, auto open browser install dist.user.js
    - full typescript support and vite feature


    https://i.songe.li/1x1.png#IyB2aXRlLXBsdWdpbi1tb25rZXkKCjxwPgogIDxhIGhyZWY9Imh0dHBzOi8vd3d3Lm5wbWpzLmNvbS9wYWNrYWdlL3ZpdGUtcGx1Z2luLW1vbmtleSI+PGltZyBzcmM9Imh0dHBzOi8vaW1nLnNoaWVsZHMuaW8vbnBtL3Yvdml0ZS1wbHVnaW4tbW9ua2V5LnN2ZyIgYWx0PSJucG0gcGFja2FnZSI+PC9hPgogIDxhIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS9saXNvbmdlL3ZpdGUtcGx1Z2luLW1vbmtleS9yZWxlYXNlcy8iPjxpbWcgc3JjPSJodHRwczovL2ltZy5zaGllbGRzLmlvL25vZGUvdi92aXRlLXBsdWdpbi1tb25rZXkuc3ZnIiBhbHQ9Im5vZGUgY29tcGF0aWJpbGl0eSI+PC9hPgo8L3A+CgpbUkVBRE1FXShSRUFETUUubWQpIHwgW+S4reaWh+aWh+aho10oUkVBRE1FX3poLm1kKQoKdml0ZSBwbHVnaW4gc2VydmVyIGFuZCBidWlsZCBcKi51c2VyLmpzIGZvciBbVGFtcGVybW9ua2V5XShodHRwczovL3d3dy50YW1wZXJtb25rZXkubmV0LykgYW5kIFtWaW9sZW50bW9ua2V5XShodHRwczovL3Zpb2xlbnRtb25rZXkuZ2l0aHViLmlvLykgYW5kIFtHcmVhc2Vtb25rZXldKGh0dHBzOi8vd3d3LmdyZWFzZXNwb3QubmV0LykKCiMjIGZlYXR1cmUKCi0gc3VwcG9ydCBUYW1wZXJtb25rZXkgYW5kIFZpb2xlbnRtb25rZXkgYW5kIEdyZWFzZW1vbmtleQotIGluamVjdCB1c2Vyc2NyaXB0IGNvbW1lbnQgdG8gYnVpbGQgYnVuZGxlCi0gYXV0byBvcGVuIFwqLnVzZXIuanMgaW4gZGVmYXVsdCBicm93c2VyIHdoZW4gdXNlcnNjcmlwdCBjaGFuZ2UKLSBleHRlcm5hbCBjZG4gdXJsIGluamVjdCB0byB1c2Vyc2NyaXB0IEByZXF1aXJlCi0gdXNlIEdNX2FwaSBieSBFU00gaW1wb3J0IHdpdGggdHlwZSBoaW50cwotIHdoZW4gdml0ZSBwcmV2aWV3LCBhdXRvIG9wZW4gYnJvd3NlciBpbnN0YWxsIGRpc3QudXNlci5qcwotIGZ1bGwgdHlwZXNjcmlwdCBzdXBwb3J0IGFuZCB2aXRlIGZlYXR1cmU=
    lisongeee
        17
    lisongeee  
    OP
       2022-08-18 17:51:57 +08:00
    lisongeee
        18
    lisongeee  
    OP
       2022-08-18 21:05:33 +08:00
    lisongeee
        19
    lisongeee  
    OP
       2022-08-19 18:37:05 +08:00
    测试 `tab` 缩进是否会被去掉
    ```ts
    (() => {
    const blankReg = /[\n\r]+/g;
    Array.from(
    document.querySelectorAll<HTMLElement>('div.reply_content')
    ).forEach((div) => {
    const mdText = div.innerText;
    const article = document.createElement('article');
    article.classList.add('markdown-body');
    article.innerHTML = 'markdownItInstance.render(mdText)';
    if (
    article.innerText.replace(blankReg, '') == mdText.replace(blankReg, '')
    ) {
    // 渲染后无变化不执行替换
    return;
    }
    article.style.width = '100%';
    div.innerHTML = '';
    div.classList.add('v2ex-comment-markdown');
    div.appendChild(article);
    });
    })();

    ```
    lisongeee
        20
    lisongeee  
    OP
       2022-08-19 18:40:14 +08:00
    测试微博图床链接是否会被 v2 转成图片

    >

    lisongeee
        21
    lisongeee  
    OP
       2022-08-19 18:44:36 +08:00
    ?k=v#hashaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
    wxf666
        22
    wxf666  
       2022-08-19 19:08:06 +08:00
    测试 # 后跟 base64

    #base64

    测试主机名后直接跟 base64

    https://sinaimg.cn/base64

    https://wx3.sinaimg.cn/base64
    wxf666
        23
    wxf666  
       2022-08-19 19:10:21 +08:00
    这是直接吃掉微博图片了吗

    测试主机名后跟两个 base64

    https://sinaimg.cn/base64/base64

    https://wx3.sinaimg.cn/base64/base64
    lisongeee
        24
    lisongeee  
    OP
       2022-08-19 19:40:33 +08:00
    测试把 base64 放在 basename 上,这是错误的图片链接

    lisongeee
        25
    lisongeee  
    OP
       2022-08-19 19:44:39 +08:00
    @wxf666

    还有一个方法就是把 base64 放在 `wx3.sinaimg.cn/mw2000/${base64Str}.jpg` 这样

    然后 v2 会自己把这个链接转图片,好处是 源信息传递出去了

    坏处是在外部视角你发的这条评论 底部会显示一个裂开的图片,具体效果是这样

    wxf666
        26
    wxf666  
       2022-08-19 20:30:59 +08:00
    @lisongeee 要不,用点零宽字符啥的?*(但零宽字符太少了)*

    或者,引入压缩库?*(感觉短文本压缩效率应该也不理想)*

    那摸清会吃掉哪些字符*(如行首空格,连续空格)*,提前用零宽字符代替?
    lisongeee
        27
    lisongeee  
    OP
       2022-08-22 10:24:06 +08:00
    lisongeee
        28
    lisongeee  
    OP
       2022-08-22 10:24:21 +08:00
    lisongeee
        29
    lisongeee  
    OP
       2022-08-22 10:24:35 +08:00
    lisongeee
        30
    lisongeee  
    OP
       2022-08-22 10:25:49 +08:00
    lisongeee
        32
    lisongeee  
    OP
       2022-08-22 10:27:50 +08:00
    lisongeee
        33
    lisongeee  
    OP
       2022-08-22 10:28:07 +08:00
    lisongeee
        35
    lisongeee  
    OP
       2022-08-22 10:32:51 +08:00
    lisongeee
        36
    lisongeee  
    OP
       2022-08-22 10:33:14 +08:00
    lisongeee
        37
    lisongeee  
    OP
       2022-08-22 11:12:44 +08:00
    ```ts
    const mdCodeReg = /```.+?```/g;
    const replyForm = document.querySelector<HTMLFormElement>(`#reply-box form`)!;
    const textarea = replyForm.querySelector('textarea')!;
    replyForm.addEventListener('submit', () => {
    if (!mdCodeReg.test(textarea.value)) {
    return;
    }

    textarea.value +=
    '\n' +
    `https://wx3.sinaimg.cn/base62/${base62.encode(
    tec.encode(textarea.value)
    )}.jpg`;
    });
    ```
    lisongeee
        38
    lisongeee  
    OP
       2022-08-22 11:26:38 +08:00
    lisongeee
        39
    lisongeee  
    OP
       2022-08-22 11:33:27 +08:00
    @wxf666

    我尝试使用 https://wx3.sinaimg.cn/base62/ xxx .jpg` 去保存信息,但是一旦使用次数过多,v2 便会提醒不要在评论中包含外链,所以用图片保存信息不太行
    lisongeee
        40
    lisongeee  
    OP
       2022-08-22 15:56:23 +08:00
    # 代码高亮及其自动格式化测试

    ## js

    ```js
    const markdownItInstance = markdownit({
    highlight(str, lang) {
    lang = lang.toLowerCase();
    if (lang2parser[lang]) {
    console.log({ str, lang });
    try {
    str = prettier.format(str, {
    parser: lang2parser[lang],
    plugins,
    });
    } catch {}
    }
    if (lang && hljs.getLanguage(lan)) {
    try {
    return hljs.highlight(str, { language: lang }).value;
    } catch (__) {}
    }
    return '';
    },
    });
    ```

    ## ts

    ```ts
    const plugins: Plugin[] = [
    parserBabel,
    parserYaml,
    parserHtml,
    parserPostcss,
    parserJava,
    ];

    const lang2parser: Record<string, BuiltInParserName | string> = {
    js: 'babel',
    jsx: 'babel',
    ts: 'babel-ts',
    tsx: 'babel-ts',
    json: 'json',
    json5: 'json5',
    yaml: 'yaml',
    html: 'html',
    vue: 'vue',
    scss: 'scss',
    css: 'css',
    less: 'less',
    java: 'java',
    };
    ```

    ## Java

    ```java
    public class HelloWorld {
    public static void main(String[] args) {System.out.println("Hello World!");;;;;}

    @Override
    public String toString() {
    return "Hello World";
    }
    public int sum(int argument1,int argument2,int argument3,int argument4,int argument5
    ) {
    return argument1+argument2+ argument3 +argument4 + argument5;
    }
    }
    ```
    wxf666
        41
    wxf666  
       2022-08-22 22:10:55 +08:00
    @lisongeee 我觉得在行首 /多个空白字符间,加入零宽字符,是可取的。如:

    > <零宽><空格><零宽><空格><零宽><空格><零宽><空格>return<空格>'ok'

    插件去掉 <零宽> 后,就能让代码渲染器正常工作了


    优点:

    1. <空格>应该不会被 v 站 吃掉
    2. 对于未装插件的人而言,视觉上没有影响
    3. 额外占用的空间不多


    缺点:

    1. 未装插件的人,直接复制代码,会有<零宽>阻碍正常运行,但又肉眼不可见,可能找不到问题所在?
    lisongeee
        42
    lisongeee  
    OP
       2022-08-23 14:21:58 +08:00
    @wxf666

    v1.1.0 更新日志
    由于 V2EX 会删除评论代码缩进, 因此插件会自动格式化代码, 支持的语言有 js/jsx/ts/tsx/json/json5/html/vue/scss/css/less/java
    ltkun
        43
    ltkun  
       2022-08-23 15:49:06 +08:00
    ### 帅气的 OP!
    duanluan
        44
    duanluan  
       2022-09-23 17:00:37 +08:00
    有没有交流群或者什么的
    lisongeee
        45
    lisongeee  
    OP
       2022-09-23 17:12:52 +08:00
    @duanluan 这东西要啥交流群啊?有问题直接去 issues 问就行,个人感觉交流群没有代码的感觉
    duanluan
        46
    duanluan  
       2022-09-23 17:20:39 +08:00
    @lisongeee issues 提使用上的疑问总感觉有点突兀,搞个交流群也适合快速反馈想法、问题,也方便新手更快入门,就坚持使用下来了。
    lisongeee
        47
    lisongeee  
    OP
       2022-09-23 17:36:56 +08:00
    谢谢,你说的交流群我感觉更适合 app 这种较大型项目,我这个插件并没有很多功能,我觉得文档和例子已经很详细

    不过我刚刚把项目的 [discussions]( https://github.com/lisonge/vite-plugin-monkey/discussions) 打开了,不想用 issues 可以用这个

    其实我仔细思考了一下,觉得你说的还是挺有道理的,但我是个咸鱼懒狗,对交流群这种兴趣不大,抱歉
    duanluan
        48
    duanluan  
       2022-09-23 17:38:45 +08:00
    就是你回复过我的主题,你也看到了我那个仓库是一个 webpack 底下有多个 tampermonkey 项目,然后还有公共的 utils 目录,同时设置了别名,以供这三个项目调用,但是用 vite 的话我就不太清楚要怎么搞了,不太好迁移。
    lisongeee
        49
    lisongeee  
    OP
       2022-09-23 17:57:54 +08:00
    @duanluan
    > 就是你回复过我的主题,你也看到了我那个仓库是一个 webpack 底下有多个 tampermonkey 项目,然后还有公共的 utils 目录,同时设置了别名,以供这三个项目调用,但是用 vite 的话我就不太清楚要怎么搞了,不太好迁移。

    我认为 `单个仓库里有多个油猴脚本的项目结构` 其实很适合 我这个插件使用的 pnpm [monorepo]( https://juejin.cn/post/6944877410827370504) ,这个和用 vite 还是 webpack 构建没有关系。

    vue/vite/element/react 以及很多知名的框架都是这种 monorepo 结构,评论篇幅太小不好展开说

    至于你说的 `不太好迁移` ,如果你乐意,我可以帮你迁移并发起 pulls
    duanluan
        50
    duanluan  
       2022-09-23 18:05:27 +08:00
    @lisongeee
    > 我可以帮你迁移并发起 pulls
    好耶!那自然是最好啦!!
    lisongeee
        51
    lisongeee  
    OP
       2022-09-24 17:58:29 +08:00
    @duanluan
    > 好耶!那自然是最好啦!!

    <https://github.com/duanluan/tampermonkey-scripts/pull/1>
    marvincible
        52
    marvincible  
       2023-05-23 12:58:21 +08:00
    mark ,我也开发了好几个自用的油猴脚本了,每次都是从 0 开始,甚至 ui 都是纯 js 撸,太 low 了
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     2480 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 30ms UTC 10:43 PVG 18:43 LAX 02:43 JFK 05:43
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86