在整体 Typescript 接口或类型定义中是否有标准模式来断言属性要么一起出现要么根本不出现?
例如,一个项目可能是有效的,如果它看起来像这样......
{
id:"ljklkj",
spellcheck:true,
spellcheckModel:"byzantine",
}
Run Code Online (Sandbox Code Playgroud)
...或这个...
{
id:"ljklkj",
}
Run Code Online (Sandbox Code Playgroud)
但是,如果任何一个拼写检查属性单独发生,则它是无效的。
{
id:"ljklkj",
spellcheckModel:"byzantine",
}
Run Code Online (Sandbox Code Playgroud)
{
id:"ljklkj",
spellcheck:true,
}
Run Code Online (Sandbox Code Playgroud)
整体式
当然,上面的简单情况可以通过创建一个 Data 和一个 SpellcheckData 类型或接口来解决。然而,在我的应用案例中,将有多个共现属性的“集群”。为每个共现组合定义一个新类型会导致类型爆炸,以表达这种情况。
出于这个原因,我将该解决方案称为“整体式”接口。当然,可能需要使用某种形式的组合来定义它。
我试过的
我试图在 Typescript 语言参考中找到这样的例子,但不知道该功能可能被称为什么(或者实际上,如果它是一个可以表达的功能),我很挣扎。属性可以是单独可选的,但我看不到表达共现的方式。
相关技术
此处讨论了 XML 数据验证的等效功能... https://www.w3.org/wiki/Co-occurrence_constraints
对于 JSON,我理解像 Schematron 和 Json Content Rules 这样的模式语言能够表达共同约束。
工作实例
如果我想像应用于 Solr 搜索引擎的 HTTP 参数集的共同约束情况的打字稿语法,它可能看起来像这样,表明您可以选择完全满足拼写或组参数,或者根本不-一个联合,其中每个类型都是可选的(由?表示)......
type SolrPassthru =
SolrCoreParams & (
SolrSpellParams? |
SolrGroupParams?
)
Run Code Online (Sandbox Code Playgroud)
这与下面的示例形成对比,我认为这是正确的 Typescript,但需要每组参数中的所有参数。
type SolrCoreParams = {
defType: SolrDefType,
boost: SolrBoostType,
}
type SolrSpellParams = {
spellcheck: …Run Code Online (Sandbox Code Playgroud) 我正在尝试为包含逗号分隔值的字符串定义 Typescript 模板文字。我能让这个定义真正递归和通用吗?
请参阅此打字稿游乐场来尝试该案例。
每个逗号分隔的值代表一个排序顺序,例如height asc。该字符串应定义一个顺序(包括一级、二级、三级等),该顺序可以根据有效字段名称和两个可能的排序"asc"和 的并集包含无限多个排序级别"desc",并按照示例代码中的示例以逗号分隔。
下面的实现最多处理 4 个排序顺序,但案例 5 表明它并不是真正的递归。当前扩展 (2x2) 的数量最多仅包含 4 个可能的值,因此幸运地处理了我尝试的初始情况。
const FIELD_NAMES = [
"height",
"width",
"depth",
"time",
"amaze",
] as const;
const SORT_ORDERS = [
"asc",
"desc",
] as const;
type Field = typeof FIELD_NAMES[number];
type Order = typeof SORT_ORDERS[number];
type FieldOrder = `${Field} ${Order}`
type Separated<S extends string> = `${S}${""|`, ${S}`}`;
type Sort = Separated<Separated<FieldOrder>>;
/** SUCCESS CASES */
const sort1:Sort = "height asc"; …Run Code Online (Sandbox Code Playgroud) 我最近遇到了一个 API,其中的数组由任意数量的重复元组构成。我尝试了一些替代方法来实现它,但遇到了具有无限递归或只是不表达约束的类型的问题。
我如何能够按照下面的情况输入 RepeatedTuple?
//Possibly a recursive conditional way to define RepeatedTuple?
// https://github.com/microsoft/TypeScript/pull/40002
type Example = RepeatedTuple<[string,number]>;
const example0:Example = [];
const example1:Example = ["hello",1];
const example2:Example = ["hello",1,"hello",2];
const example3:Example = ["hello",1,"hello",2,"hello",3];
const example4:Example = ["hello",1,"hello",2,"hello",3,"hello",4];
Run Code Online (Sandbox Code Playgroud)
为什么这个命令行中的重定向操作显然被bash忽略了?我的目标是将标准错误重定向到标准输出,然后将整个批次输入空白.
( cd ../src/ && python -m SimpleHTTPServer 8000 2>&1 > /dev/null ) &
Run Code Online (Sandbox Code Playgroud)
我在一些静态Web内容上运行SimpleHTTPServer,以便wget可以检查它是否有死链接.但是,我不希望看到来自服务器的错误(对失败页面的请求),因为wget日志文件提供了我需要的所有信息.
不过,当我跑这个......
( cd ../log/ && wget --quiet --spider --recursive -o spider.log http://localhost:8000/ 2>&1 > /dev/null )
Run Code Online (Sandbox Code Playgroud)
...在后台运行的原始SimpleHTTPServer命令继续喷出有关失败的资源请求的标准错误报告,如...
127.0.0.1 - - [28/May/2013 17:22:31] "GET /technology/actuator.html HTTP/1.1" 200 -
127.0.0.1 - - [28/May/2013 17:22:31] code 404, message File not found
Run Code Online (Sandbox Code Playgroud) 我不知道如何使用yield(不yield from)包装子生成器而不阻止send()工作.使用yield from允许send()继续使用子生成器,但它移交控制,你无法检查或计算通过的值.
动机:我使用python3生成器编写了一些流迭代,允许文件或套接字或其他任何东西通过一个通用的"接口"一次读取一个字节,以便解析器逐个使用字节.
为了帮助解析我然后扩展了生成器逻辑,以便允许请求者可以指示流在产生字节之后是否应该增加其位置(字节被读取和消耗),或者流是否应该在屈服之后保持其位置(窥视 - 该字节只能读取).这样就可以在将流传递给子解析器之前匹配规则.
在当前实现中,以下任何一个都将从生成器获取一个字节并增加生成器在流中的位置.
byte = stream.send(True)
byte = next(stream)
Run Code Online (Sandbox Code Playgroud)
...此特殊调用从生成器获取一个字节而不增加流中的位置.
byte = stream.send(False)
Run Code Online (Sandbox Code Playgroud)
到现在为止还挺好.我的低内存JSON解析器(https://github.com/ShrimpingIt/medea)运行良好.https://github.com/ShrimpingIt/medea/blob/dd0007e657cd487913c72993dcdaf0f60d8ee30e/examples/scripts/twitterValuesNamed.py上的示例能够处理来自文件的缓存推文.
在HTTPS的情况下 - 要从套接字获取实时推文,SSL套接字不会在结束时自动关闭.任何解析过程只是挂起等待更多数据,我想修复.
出于这个原因,我首先创建HTTPS流,然后从流中读取字节,处理内容长度标头并跳转到HTTP标头末尾的"\ r \n\r \n",然后将流处理到正确的位置到解析器.此时我知道流在停止之前应该服务多少内容字节.
不幸的是,我遇到了语法,表达或理解问题.
直接移交给流很容易,并且保留了发送功能(允许查看字节)...
def delegatingStream():
yield from rawStream
Run Code Online (Sandbox Code Playgroud)
但是,我无法想象如何创建一个迭代器,智能地使用contentLength值在contentLength之后终止而不破坏send().
我需要使用yield能够干预迭代器逻辑,但yield from似乎只允许委派send().我甚至无法一起发送和收集来复制delegatingStream()的行为.例如,这不具有相同的效果.
def relayingStream():
while True:
yield rawStream.send((yield))
Run Code Online (Sandbox Code Playgroud)
避免的原因yield from是我最终需要这样的实现,(这并不忠实地转发send())...
def terminatingStream():
contentPos = 0
while contentPos < contentLength:
increment = (yield)
yield rawStream.send(increment)
if increment is not False:
contentPos …Run Code Online (Sandbox Code Playgroud) 我想将 HTTP POST 值直接作为 JSON 发送到已在我的 GraphQL Mutation 中声明的 addBook 解析器。
但是,我见过(并证明)的示例使用从 JSON 到 SDL 的参数序列化或在 SDL 中重新声明变量以从查询变量进行绑定。
这两种方法都没有意义,因为 addBook 突变已经声明了所有参数和验证。使用这些方法将导致必须创建、调试和维护不必要的查询序列化逻辑。
我在浏览器中构造了格式良好(模式编辑和验证)的 JSON,它符合声明的 GraphQLObjectType 的数据。
谁能解释在针对突变解析器发布时如何避免这种不必要的重新序列化或重复?
我一直在尝试使用多种方法将 JSON 数据结构映射到 addBook 突变,但找不到简单发送 JSON 的示例,以便将属性名称绑定到 addBook 参数名称,而没有明显毫无意义的重新序列化或样板。
https://github.com/cefn/graphql-gist/tree/master/mutation-map 上的源代码是一个最小的可重现示例,它演示了该问题。它有一个 addBook 解析器,它已经定义了参数名称、类型和可空性。我找不到使用 JSON 来简单地针对 addBook POST 参数的方法。
我使用 GraphiQL 作为 HTTP POST 值的参考实现。
我可以编写代码将 JSON 序列化为 SDL。它最终看起来像这样,它通过 GraphiQL 工作:
mutation {addBook(id:"4", name:"Education Course Guide", genre: "Education"){
id
}}
Run Code Online (Sandbox Code Playgroud)
或者,我可以编写代码将 addBook 的每个参数显式别名为不同的查询,然后允许我将值作为 JSON 查询变量发布,也通过 GraphiQL 证明:
mutation doAdd($id: String, $name: String!, $genre: String){ …Run Code Online (Sandbox Code Playgroud)