Switchyomega: 虚拟Profile的同步问题

Created on 27 Jan 2016  ·  16Comments  ·  Source: FelisCatus/SwitchyOmega

现有的同步,在不同的机器上,当前选择的Profile不进行同步。这个是对的。
因为考虑多Profile的最多的应用场景是规则相同,但是在不同的PC上(比如公司和家里),要选用不同的Profile。

但是应用了虚拟Proflie时,虚拟Profile的选择会进行同步,这个应该也不同步才对。
考虑如下场景:三个Proxy Profile,在不同的机器上使用,家里,公司等。
同一套规则,都是为了FQ。所以再建一个Auto Swicth和一个虚拟Profile,Auth Switch指向虚拟Profile。
虚拟Profile在不同机器上的选择,不希望同步。

All 16 comments

我觉得可以理解这个用例……在此例中,虚拟情景模式相当于代替了当前情景模式,是属于不同机器的状态。

暂时而言,唯一的解决方案是完全不要重叠使用。也就是说,建立两个 Switch 和两个虚拟情景模式分别用。然而这需要维护两个 Switch ,会很麻烦。

从产品设计的角度来说,我个人比较倾向于设计成每个情景模式都可以开启/关闭同步,但这在技术上难度比较高,有很多意料不到的情况。技术细节见下。


虚拟情景模式的数据包括名字和目标两个属性,是配置的一部分(而非状态的一部分),所以默认肯定是同步的。考虑这个情况:虚拟情景V指向了情景模式A(V->A),此时如果将情景模式A改名为B,则虚情景模式也需要更新成(V->B)。如果V不同步,则在另外的设备上A已经变成了B,但V仍然是(V->A),会导致数据不一致。同理也适用于A被删除之类的情况。更可怕的是这很容易造成死循环……(V1->V2, V2->V1)

而当前选择的情景模式属于状态,无论当前情景模式指向什么名字,都不会影响一致性。唯一可能出现的问题是当前情景模式指向了不存在的情景,那种情况已经特殊处理了,会自动选取系统情景。而且唯一读取当前情景的时机是在启动时,这很容易控制。

这种情景模式导致不一致的问题,不仅仅出现在虚情景上。自动切换模式也有此问题,因为自动切换中也指向了其他情景模式。自动切换的问题可能更严重,因为指针不止一个(在每条规则里都有),而且自动切换可以有对应的规则列表,而规则列表是分开同步的。规则列表本身也有两个指针(匹配和不匹配)。

SO 做了很多处理和检查来保证设置的一致性,比如在选项中禁止构成循环引用。不过这些检查都是将配置文件作为一个整体进行的,而且只有检查本地的情况。假如允许手动开启/关闭一部分情景模式的同步,那么每个设备上都会不同,且云端存储的版本也不同,会有 N + 1 种复杂情况。再加上目前的代码大部分都是在界面的层面上做限制,同步下载后必然会导致很多意外的结果。

即使只允许关闭虚情景的同步,这也将打开潘多拉的魔盒。加一个按钮/选择框自然没这么难,难的是之后用户的配置文件被毁了要怎么办。所以我个人倾向于避免推出这种很明显会触发不定时炸弹的功能,或者至少推迟到设置一致性的问题能得到更好的解决。

谢谢回复。就此问题来看,我觉得还是设计的太复杂了,又有多少人有这么复杂的需求。。。特意看了下周围同事的设置,基本就是一两条规则,懒的直接手动切,好一点儿的就设一个auto的。

然而试过您说的建两个switch和两个virtual,当然,这是现在可以的唯一解决方案,但是已经感觉晕了,我尝试向同事们解释这种配置的方便性,有些同事还觉得太晕,呵呵。而两个Switch维护也很麻烦。

然后Virtual的,还有些问题,比如,如果一个Virtaul1指向一个Switch1,另一个Switch2又使用这个Virtual1,那会是什么效果呢?还有如果Virtual1指向Virtual2的呢?

好吧,当我看成到SwitchyOmega有一个Virtual的Profile时,说实话,看了好久没明白怎么用,最后还是在Issue里找到相关的用法。所以,我提出一个更大胆的想法,Virtual能简化一下吗?

  1. Virtual的里Replace Target Profile,可以做成工具,不要和Virtual相关。选择一个Switch,然后选选择Src和Dst,就是把一个Switch里的Src Profile替换成Dst Profile。(好吧,其实如果大家用好了Virtual,这个其实是没有必要的,只是有人不会用Virtual才需要这个工具)
  2. Virtual只能指向Direct,System和普通Profile,不能指向Switch和另一个Virtual。(实在没想明白,有哪些应用场景需要这样的配置?也有可能是我的环境还是简单的,有更复杂的用法。。。。但是,用这个的,感觉90%是用来FQ的吧,嘿嘿)
  3. 其实可以不用允许新建Virtual,就只有一个系统内置的Virtual,比如叫Alternate,和Direct以及System平级。不使用Virtual的时候,就只有原来普通的Profile和Switch。Switch的规则里,可以设成Direct,System以及Alternate和普通的Profile。然后Alternater是一个状态,选择其中一种普通Profile,不存在时,就指向Direct或System。

最后,说了这么多,不得不说明,也许这只是我的需求和看法,有更多人的有更复杂的应用。那就全当我没说吧 。。。不知道SwitchyOmega有没有办法统计配置的复杂度?一开始我也觉得设计要做的越强大越适普越好,但是后来慢慢的变了,感觉如果为了1%的应用,而让99%的人配置变得很复杂,其实就是得不偿失。。。就好比Android和iPhone,Windows和MacOS

Virtual 这个事情本来设计的就有点复杂,解释起来需要指针或者引用之类的说法,我并不是特别喜欢。换成 Alternate 的设计也许更好,不过前提是功能要比现在容易理解。此外,我估计又要有很多人抱怨为何不可两个 Alternate 之类的……(之前出现过有不少人想要多 Switch Profile ,所以 SwitchyOmega 才重新设计了设置模型。)

1: Replace: 我觉得这个可以有,不过估计用这个功能的人也不会特别多。正如您所说,合理使用 Virtual / Alternate 可以很轻易地解决这个问题。此外用户体验和性能更好。

2: 然而问题是并没有办法在代码层面上强制只能指向普通 Profile。任何 Profile 的唯一标识都是名称。先指向普通 Profile 再因为同步差异变成指向同名的另一个 Switch 也是有可能的。

我觉得适当的统计和反馈数据是应该要有的(前提是用户同意分享),这对于以后的设计有很多帮助。

但是另一方面,我不希望做任何 Breaking Change. 已经有的设置,无论情况多么罕见,必须能继续正常工作,界面上和功能上都是。这不意味着不能做任何功能修改,但修改后必须向后兼容。将 Virtual 改成 Alternate 的修改,很遗憾是不向后兼容的,已有的配置也无法自动迁移到新配置。最最激进的方案,恐怕也只能把新增 Virtual Profile 的功能从界面上隐藏掉,而已经存在的仍然可以正常修改和使用。

一个之前的案例:SO曾经有独立的“规则列表情景模式”。由于这个配置起来太复杂,而且一般大家都是与自动切换一起用,所以这个功能最后取消了。具体的迁移方式是:1.隐藏新建规则列表情景模式的入口,2.自动切换中内嵌规则列表的全部功能, 3.已经新建的规则列表情景模式仍然可以正常修改和使用。

这个看怎么说,不改Virtual,也可以增加一个Alternate与System/Direct平级,然后这个的指向做为状态而不是配置存储不就ok了?:)
顶多就是用户会感觉Virtual和Alternate在功能上有重叠,在只使用一个Virtual的情况下,可以建议用户选择Alternate,这样就能兼顾了~

Alternate 这个名字我不是很满意……用户恐怕很难明白是什么意思。
(虽然Virtual的意思也不是很明确啦……)

名字而已,叫什么无所谓,功能才是重点~。。。Delegate(委托)?

好吧,确实Virtual也不太好,反正第一次用时,好久都没明白什么意思,幸好Issue里有人提过,有说明。。。Virtual的创建页面加一小段用法说明就好了。

创建 Virtual Profile 的提示:

A virtual profile can act as any of the other profiles on demand. It works well with SwitchProfile, allowing you to change the result of multiple conditions by one click.

也有中文翻译。

我觉得可以新功能可以叫 ☆ Favorite Proxy ,然后每个 Proxy Profile 那边可以点 ☆ 来设置成最喜欢/常用的 Proxy 。 ←脑洞

关于Virtual,我中文的英文的提示都看过。。。都没明白是怎么回事儿:P
然后这个设置页面简单,就一个指向,所以一开始实在没想明白和Switch有啥区别。然后下面有一个工具,一开始总觉得是上面选定一个Switch,然后用下面的工具来替换呢,所谓"by one click",哈哈。

所以我觉得说明应该再加一段,说明Switch可以选择一个Virtual的Proxy,然后由Virtual来确定实际的用的是那个Proxy。。。其实就功能而言,这个更像是 委托代理,设计模式中的一种。。。这个名字更好些,呵呵。

对于Virtual,我觉得在建立Profile的页面里,应该往上移,放到Porxy Profile的下面会好一些。
我建立Profile时,看到Virtual在最后,又是新加的,再加上这么高大上的名字。。。所以潜意识里就觉得这是个比Switch更高级的东西,所以一直没想过把这个Profile用到Switch里,而是觉得这个里面应该可以包含Switch,一直往这条路想的。可能这也是说明看不懂,不知道怎么用的一个原因。:)

也遇到这个问题。也想到建2套 Switch Virtual 。这样的话 2个 Switch的规则不能互通。

名字换成 Bridge?

Alternate 这个名字我不是很满意……用户恐怕很难明白是什么意思。(虽然Virtual的意思也不是很明确啦……)

写了个PAC` 来解决。

`

function FindProxyForURL(url, host) {
if (host === "127.0.0.1" || host === "::1" || host.indexOf(".") < 0) return "DIRECT";
//家
if (isInNet(myIpAddress(), "192.168.9.0", "192.168.9.255")) return "SOCKS5 my-home-proxy:10800; SOCKS my-home-proxy:10800";
//公司
return "SOCKS5 office-proxy:10800; SOCKS office-proxy:10800";
}

`

话说根据 IP 地址/代理服务器是否在线之类的来切换可以看 #197 的讨论和代码示例。

到家发现自己写的PAC不管用
将 PAC 保存成文件 Firefox调试 是可以使用的。
难道说 Chrome(SwitchyOmega) 和 Firefox 下 myIpAddress() 结果是不一样的?
缺乏Chrome(SwitchyOmega)下调试PAC 手段所以放弃了shExpMatch( myIpAddress) 方法。
现在用isResolvable() 函数判断 NetBIOS主机名。来切换代理。
感觉比IP地址更科学。目前现在家里几台PC都正常。节后去公司再看看。

嗯, myIpAddress() 很坑的,浏览器之间实现可能会不同, #197 里稍微提到了一些。尤其是, myIpAddress() 可以返回 127.0.0.1 或者在 IPv4 环境下返回机器的内部 IPv6 地址之类的,这样会使得判断逻辑失效。

Was this page helpful?
0 / 5 - 0 ratings

Related issues

FormosaZh picture FormosaZh  ·  3Comments

FelisCatus picture FelisCatus  ·  4Comments

GF-Huang picture GF-Huang  ·  3Comments

zwdzwdzwd picture zwdzwdzwd  ·  3Comments

FelisCatus picture FelisCatus  ·  3Comments