I want configure the Dart Editor for the formatting a such source code without a breaking the first line on parameter list.
Result of formatting.
String _expand(
List fragments, Map<String, MacroDefinition> definitions, String defaultValue, Set<String> processed) {
//
}
Is this possible in Dart Editor?
String _expand(List fragments, Map<String, MacroDefinition> definitions, String defaultValue,
Set<String> processed) {
//
}
P.S.
The above source code formatted with a 120 characters per line.
You can't configure anything but the line length in DartFormat. It was a deliberate decision to not support formats which deviate from the default format.
Related
We use i18next in a CMS to power its internationalization features. Since developers can build however they want with the CMS there is opportunity for them to add l10n keys that include colons, including as part of HTML, such as Find more info here.
As has been documented, with default namespace separator settings i18next will think the colon is identifying a namespace/key pair. Since the CMS uses its own namespace (so devs won't accidentally overwrite UI strings), we don't have the option to turn off namespacing completely (with nsSeparator: false).
What I'm looking for is a way for i18next to only recognize registered namespaces as namespaces. So if we tell i18next that the valid namespaces are ['ns1', 'ns2'] and it receives Title: Subtitle, that string will be treated as a key, not a namespace/key pair.
I saw the loadNamespaces method, but that looks to simply register them to the ns option on the instance. Is there a way for i18next to essentially disallow any unregistered namespace?
This is definitely a workaround, but it doesn't feel too hackey, so I was comfortable using it indefinitely. It's been several weeks, so I don't remember if I got this from somewhere else, but it's possible, for the sake of not taking the credit if undeserved.
First, I added the appendNamespaceToMissingKey: true option to the init function. This adds the default namespace to any keys that don't already have a namespace. It also includes an unknown namespace (or something it thinks is a NS) with the "missing key" for parsing.
Then I added the parseMissingKeyHandler option assigned to the following function:
function (key) {
if (key.startsWith(`${this.defaultNS[0]}:`)) {
return key.slice(this.defaultNS[0].length + 1);
} else {
return key;
}
}
Since I didn't have to hard-code the namespace I felt okay with that.
So if a "key" comes in here with the default namespace, which will include all unlocalized strings without colons (e.g., 'Some text'), that namespace is removed and the string continues on normally. Since i18next doesn't have a value for that string, the string is printed as-is.
If an unlocalized string comes in containing a colon (e.g., '🏛', i18next thinks the first part before the colon is a namespace, so the default is not applied. Therefore this colon-ized string is returned from the function the same as it entered. Again, since i18next doesn't have a value for this string, the string is printed as-is. In this case, that includes the part before the colon as well as the colon separator. We end up with the full link HTML, for example.
So in addition to the other options in place, it looks like:
i18next.init({
...otherOptions,
appendNamespaceToMissingKey: true,
parseMissingKeyHandler (key) {
// We include namespaces with unrecognized l10n keys using
// `appendNamespaceToMissingKey: true`. This passes strings containing
// colons that were never meant to be localized through to the UI.
//
// Strings that do not include colons ("Content area") are given the
// default namespace by i18next ("translation," by default). Here we
// check if the key starts with that default namespace, meaning it
// belongs to no other registered namespace, then remove that default
// namespace before passing this through to be processed and displayed.
if (key.startsWith(`${this.defaultNS[0]}:`)) {
return key.slice(this.defaultNS[0].length + 1);
} else {
return key;
}
}
});
I'm including my code comment since you may also want to include something like this to remind yourself later why you include this convoluted handler.
I'm using the Java syntax defined at https://github.com/antlr/grammars-v4/tree/master/java/java
My users are free to input any thing, for example
assert image != null;
,
public Color[][] smooth(Color[][] image, int neighberhoodSize)
{
...
}
,
package myapplication.mylibrary;
, and
import static java.lang.System.out; //'out' is a static field in java.lang.System
import static screen.ColorName.*;
My program should tell which syntax the input matches.
What I have up to now is
var stream = CharStreams.fromString(input);
ITokenSource lexer = new JavaLexer(stream);
ITokenStream tokens = new CommonTokenStream(lexer);
Parser parser = new JavaParser(tokens);
parser.ErrorHandler = new BailErrorStrategy();
try
{
var tree = parser.statement();
Console.WriteLine("The input is a statement");
}
catch (Exception e)
{
Console.WriteLine("The input is not a statement");
}
Are there better way to check the input match any of the 100 rules?
No, there's no other way than trial-and-error. Note that your generated parser has the property:
public static final String[] ruleNames
which you can use in combination with reflection to call all parser rules automatically instead of trying them manually.
Also, trying parser.statement() might not be enough: the input String s = "mu"; FUBAR could be properly parsed by parser.statement() and leave the trailing Identifier (FUBAR) in the token stream. After all, the statement rule probably does not end with an EOF token forcing the parser to consume all tokens. You'll probably have to manually check if all tokens are consumed before determining the input was successfully parsed by a certain parser rule. Also see this Q&A: How to test ANTLR translation without adding EOF to every rule
Unless you really mean that your users can enter anything (and I would suspect that, with some thought, that’s not really the case)
You could add a parser rule that includes alternatives for each construct your users could enter. You might have to take a little care on the order.
Since parser rules are evaluated recursive descent, if your new rule isn’t referenced by any other rules, it would have no impact on the rest of the grammar.
Could be worth a shot.
I have issue while using ObjectMapper with YAMLFactory to Parse a YAML File
The YAML file I’m trying to parse : https://drive.google.com/open?id=1Q85OmjH-IAIkordikLTsC1oQVTg8ggc8
Parsing the File using readValue as shown here :
ObjectMapper mapper = new ObjectMapper(new YAMLFactory().enable(Feature.MINIMIZE_QUOTES)//
.disable(Feature.WRITE_DOC_START_MARKER)//
.disable(YAMLGenerator.Feature.SPLIT_LINES));
TypeReference<HashMap<String, Object>> typeRef = new TypeReference<HashMap<String, Object>>() {};
HashMap<String, Object> obj = mapper.readValue(responseBuffer.toString(), typeRef);
Converting the Obj to json then to YAML again by :
JsonElement jsonElem = wrapJacksonObject(obj);
String cloudTemplateJsonString = new GsonBuilder().disableHtmlEscaping().setPrettyPrinting()//
.create()//
.toJson(jsonElem);
JsonNode jsonNode = mapper.readTree(cloudTemplateJsonString);
String yaml = new YAMLMapper().enable(Feature.MINIMIZE_QUOTES)//
.disable(Feature.WRITE_DOC_START_MARKER)//
.writeValueAsString(jsonNode);
After checking the last String, I see that these Special Characters are Changed/Deleted (they are Changed exactly after Point 2) :
a. ‘ transferred to “ or Deleted
b. ! : Regarding the exclamation mark : the whole string after it until first space is deleted totally
Examples :
Version: !Join ['-', [!Ref GatewayVersion, GW]]
After Parsing
Version:
- '-'
- - GatewayVersion
- GW
Also single Quotes sometimes Deleted / Converted to double Quote
AllowedPattern: '^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})/(\d{1,2})$'
After Parsing Single quotes Deleted :
AllowedPattern: ^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})/(\d{1,2})$
I try to use Escape Characters Customization By customizing Implementation for CharacterEscapes class but it didn’t help
In YAML, a value such as a string literal can be prepended by tokens indicating metadata about the node, known as node properties. Tokens beginning with a bang ! are considered to be 'node tags', and tokens begining with an ampersand & are 'node anchors'.
https://yaml.org/spec/1.2/spec.html#id2783797
JSON does not have an equivalent capability. Because Jackson is primarily a JSON parsing library its internal representation of structured data nodes do not have fields for metadata, and so its YAMLFactory parser implementation simply discards them.
Looking at your YAML file I expect the intended parser of the file (aws' cloudwatch cli tool?) would have known how to use those !Join and !Ref node tags to construct an internal representation of the Version field.
Similarly, single or double quotes surrounding a text value are considered to be part of the markup (i.e., used the parser) rather than part of the value. Thus the parser discards these characters (after using them as guides on how to consume the value). Quotes (double or single) may be added or not as neccessary when reserializing an internal representation back into YAML or JSON.
I hope to pass the string {"name":"My Settings 1"} to a var aa
I have to write it using the code var aa=" {\"name\":\"My Settings 1\"} "
Is there a simple way in Kotlin when I use Android Studio 3.0 ?
I know <![CDATA[...]]> is good for XML content
The simplest thing you can do in Kotlin is use raw strings with triple quote marks:
val a = """{"name":"My Settings 1"}"""
For a tooling solution instead of a language solution (so this works both in Kotlin and Java), you can use language injection in Android Studio or IntelliJ.
Create a string, and invoke intention actions on it with Alt + Enter. Select Inject language or reference, and then JSON.
Use Alt + Enter again, and choose Edit JSON Fragment.
Edit the raw JSON in the panel that appears on the bottom, and IntelliJ will automatically mirror its contents into the string, escaping any characters that have to be escaped.
Escaping special chars in regular Strings, like in your example, is what has to be done with Java and also Kotlin:
"{\"name\":\"My Settings 1\"}"
Kotlin offers raw Strings to evade this. In these raw Strings there's no need to escape special chars, which shows the following:
"""{"name":"My Settings 1"}"""
Raw Strings are delimited by a triple quote (""").
Read the docs here.
I have a generated grammar that does two things:
Check the syntax of a domain specific language
Evaluate input against that domain specific language
These two functions are separate, lets call them validate() and evaluate().
The validate() function builds the tree from a String input while ensuring it meets the requirements of the BNF for the language. The evaluate() function plugs in values to that tree to get a result (usually true or false).
What the code is currently doing is running validate() each time on the input, just to generate the tree that evaluate() uses. Some of the inputs take up to 60 seconds to be checked. What I would LIKE to do is serialize the results of validate() (assuming it meets the syntax requirements), store the serialized form in the backend database, and just load it from the database as part of evaluate().
I noticed that I can execute the method toStringTree() on the parse tree, and retrieve a LISP style tree. However, can I restore a LISP style tree to an ANTLR parse tree? If not, can anyone recommend another way to serialize and store the generated parse tree?
Thanks for any help.
Jason
ANTLR 4's ParseRuleContext data structure (the specific implementation of ParseTree used by generated parsers to represent grammar rules in the parse tree) is not serializable by default. Open issue #233 on the project issue tracker covers the feature request. However, based on my experience with many applications using ANTLR for parsing, I'm not convinced serializing the parse trees would be useful in the long run. For each problem serializing the parse tree is meant to address, a better solution already exists.
Another option is to store a hash of the last known valid file in the database. After you use the parser to create a parse tree, you could skip the validation step if the input file has the same hash as the last time it was validated. This leverages two aspects of ANTLR 4:
For the same input file, running the parser twice will produce the same parse tree.
The ANTLR 4 parser is extremely fast in almost all cases (e.g. the Java grammar can process around 20MB of source per second). The remaining cases tend to be caused by poorly structured grammar rules that the new parser interpreter feature in ANTLRWorks 2.2 can analyze and make suggestions for improvement.
If you need performance beyond what you get with this, then a parse tree isn't the data structure you should be using. StringTemplate 4's enormous performance advantage over StringTemplate 3 came primarily from the fact that the interpreter switched from using ASTs (equivalent to parse trees for this reasoning) to a linear bytecode representation/interpreter. The ASTs for ST4 would never need to be serialized for performance reasons because the bytecode would be serialized instead. In fact, the C# port of StringTemplate 4 provides exactly this feature.
If the input data to your grammar is made of several independent blocks, you could try to store the string of each block separately, and run the parsing process again for each block independently, using a ThreadPool for example.
Say for example your input data is a set of method declarations:
int add(int a, int b) {
return a+b;
}
int mul(int a, int b) {
return a*b;
}
...
and the grammar is something like:
methodList : methodDeclaration methodList
|
;
methodDeclaration : // your method declaration rules...
The first run of the parser just collects each method text and store it. The parser starts the process at the methodList rule.
void visitMethodList(MethodListContext ctx) {
if(ctx.methodDeclaration() != null) {
String methodStr = formatParseTree(ctx.methodDeclaration(), " ");
// store methodStr for later parsing
}
// visit next method list item, if any
if(ctx.methodList() != null) {
visit(ctx.methodList());
}
}
The second run launch the parsing of each method declaration (in a separate thread for example). For this, the parser starts at the methodDeclaration rule.
void visitMethodDeclaration(MethodDeclarationContext ctx) {
// parse the method block
}
The reason why the text of a methodDeclaration rule is formatted if because calling directly ctx.methodDeclaration().getText() would combine the text of all child nodes AntLR doc, possibly making it unusable for parsing again. If white space is a token separator in the grammar, then adding one space between tokens should not change the parse tree.
String formatParseTree(ParseTree tree, String separator) {
StringBuilder builder = new StringBuilder();
for(int i = 0; i < tree.getChildCount(); i ++) {
ParseTree child = tree.getChild(i);
if(child instanceof TerminalNode) {
builder.append(child.getText());
builder.append(separator);
} else if(child instanceof RuleContext) {
builder.append(formatParseTree(child, separator));
}
}
return builder.toString();
}