Cleaned up exceptions and their messages.
Some minor dog fixes.
This commit is contained in:
parent
009017eef0
commit
8ad650e089
Binary file not shown.
|
@ -105,6 +105,11 @@
|
|||
</dt>
|
||||
<dd><p>Construct a Dumper writing to a stream. This is useful to e.g. write to memory.</p>
|
||||
|
||||
</dd>
|
||||
<dt class="d_decl">@property void <a name="name"></a><span class="ddoc_psymbol">name</span>(string <a name="name"></a><span class="ddoc_psymbol">name</span>);
|
||||
</dt>
|
||||
<dd><p>Set stream name. Used in debugging messages.</p>
|
||||
|
||||
</dd>
|
||||
<dt class="d_decl">void <a name="resolver"></a><span class="ddoc_psymbol">resolver</span>(Resolver <a name="resolver"></a><span class="ddoc_psymbol">resolver</span>);
|
||||
</dt>
|
||||
|
|
|
@ -47,7 +47,7 @@
|
|||
|
||||
<dl><dt class="d_decl">this(string <b>msg</b>, string <b>file</b> = __FILE__, int <b>line</b> = __LINE__);
|
||||
</dt>
|
||||
<dd><p>Construct a YAMLException with specified message, and position where it was thrown.</p>
|
||||
<dd><p>Construct a YAMLException with specified message and position where it was thrown.</p>
|
||||
|
||||
</dd>
|
||||
</dl>
|
||||
|
|
|
@ -104,7 +104,7 @@
|
|||
<b>Parameters:</b><div class="pbr"><table class=parms><tr><td valign=top>string <b>filename</b></td>
|
||||
<td valign=top>Name of the file to load from.</td></tr>
|
||||
</table></div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException if the file could not be opened or read from.</div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException if the file could not be opened or read.</div>
|
||||
|
||||
</dd>
|
||||
<dt class="d_decl">this(Stream <b>stream</b>);
|
||||
|
@ -114,7 +114,7 @@
|
|||
<b>Parameters:</b><div class="pbr"><table class=parms><tr><td valign=top>Stream <b>stream</b></td>
|
||||
<td valign=top>Stream to read from. Must be readable.</td></tr>
|
||||
</table></div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException if <b>stream</b> could not be read from.</div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException if <b>stream</b> could not be read.</div>
|
||||
|
||||
</dd>
|
||||
<dt class="d_decl">@property void <a name="name"></a><span class="ddoc_psymbol">name</span>(string <a name="name"></a><span class="ddoc_psymbol">name</span>);
|
||||
|
@ -136,7 +136,7 @@
|
|||
</dt>
|
||||
<dd><p>Load single YAML document.
|
||||
</p>
|
||||
<p>If none or more than one YAML document is found, this will throw a YAMLException.
|
||||
<p>If none or more than one YAML document is found, this throws a YAMLException.
|
||||
|
||||
</p>
|
||||
<b>Returns:</b><div class="pbr">Root node of the document.
|
||||
|
@ -153,7 +153,7 @@
|
|||
<b>Returns:</b><div class="pbr">Array of root nodes of all documents in the file/stream.
|
||||
|
||||
</div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException on a YAML parsing error.</div>
|
||||
<b>Throws:</b><div class="pbr">YAMLException on a parsing error.</div>
|
||||
|
||||
</dd>
|
||||
<dt class="d_decl">int <a name="opApply"></a><span class="ddoc_psymbol">opApply</span>(int delegate(ref Node) <b>dg</b>);
|
||||
|
|
|
@ -69,13 +69,13 @@
|
|||
</dt>
|
||||
<dd><p>Add a function to represent nodes with a specific data type.
|
||||
</p>
|
||||
<p>The representer function takes a reference to a Node storing the data
|
||||
<p>The representer function takes references to a Node storing the data
|
||||
type and to the Representer. It returns the represented node and may
|
||||
throw a RepresenterException. See the example for more information.
|
||||
<br>
|
||||
|
||||
Only one function may be specified for one data type. Default data
|
||||
types already have representer functions unless disabled in these
|
||||
types already have representer functions unless disabled in the
|
||||
Representer constructor.
|
||||
|
||||
</p>
|
||||
|
|
|
@ -138,7 +138,7 @@ struct appears in Phobos.</p>
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -104,7 +104,7 @@
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -87,7 +87,7 @@
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -369,7 +369,7 @@ directory of the D:YAML package.</p>
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -237,7 +237,7 @@ example in the <tt class="docutils literal"><span class="pre">example/getting_st
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -330,7 +330,7 @@ Some of these might change in the future (especially !!map and !!set).</p>
|
|||
</div>
|
||||
<div class="footer">
|
||||
© Copyright 2011, Ferdinand Majerech. Based on PyYAML http://www.pyyaml.org by Kirill Simonov.
|
||||
Last updated on Oct 17, 2011.
|
||||
Last updated on Oct 18, 2011.
|
||||
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.7.
|
||||
</div>
|
||||
</body>
|
||||
|
|
|
@ -26,7 +26,7 @@ import dyaml.resolver;
|
|||
|
||||
package:
|
||||
/**
|
||||
* Marked exception thrown at composer errors.
|
||||
* Exception thrown at composer errors.
|
||||
*
|
||||
* See_Also: MarkedYAMLException
|
||||
*/
|
||||
|
@ -113,7 +113,7 @@ final class Composer
|
|||
//Ensure that the stream contains no more documents.
|
||||
enforce(parser_.checkEvent(EventID.StreamEnd),
|
||||
new ComposerException("Expected single document in the stream, "
|
||||
"but found another document: ",
|
||||
"but found another document.",
|
||||
parser_.getEvent().startMark));
|
||||
|
||||
//Drop the STREAM-END event.
|
||||
|
@ -246,6 +246,18 @@ final class Composer
|
|||
{
|
||||
Node.Pair[] result;
|
||||
|
||||
void error(Node node)
|
||||
{
|
||||
//this is Composer, but the code is related to Constructor.
|
||||
throw new ConstructorException("While constructing a mapping, "
|
||||
"expected a mapping or a list of "
|
||||
"mappings for merging, but found: "
|
||||
~ node.type.toString ~
|
||||
" NOTE: line/column shows topmost parent "
|
||||
"to which the content is being merged",
|
||||
startMark, endMark);
|
||||
}
|
||||
|
||||
if(root.isMapping)
|
||||
{
|
||||
Node[] toMerge;
|
||||
|
@ -259,32 +271,15 @@ final class Composer
|
|||
merge(result, flatten(node, startMark, endMark));
|
||||
}
|
||||
}
|
||||
else if(root.isSequence)
|
||||
//Must be a sequence of mappings.
|
||||
else if(root.isSequence) foreach(ref Node node; root)
|
||||
{
|
||||
//Must be a sequence of mappings.
|
||||
foreach(ref Node node; root)
|
||||
{
|
||||
//this is Composer, but the code is related to constructor
|
||||
enforce(node.isType!(Node.Pair[]),
|
||||
new ConstructorException("While constructing a mapping, " ~
|
||||
"expected a mapping for merging, but found"
|
||||
~ node.type.toString ~
|
||||
"NOTE: line/column shows topmost parent "
|
||||
"to which the content is being merged",
|
||||
startMark, endMark));
|
||||
merge(result, flatten(node, startMark, endMark));
|
||||
}
|
||||
if(!node.isType!(Node.Pair[])){error(node);}
|
||||
merge(result, flatten(node, startMark, endMark));
|
||||
}
|
||||
else
|
||||
{
|
||||
//this is Composer, but the code is related to constructor
|
||||
throw new ConstructorException("While constructing a mapping, " ~
|
||||
"expected a mapping or a list of mappings for "
|
||||
"merging, but found: "
|
||||
~ root.type.toString ~
|
||||
"NOTE: line/column shows topmost parent "
|
||||
"to which the content is being merged",
|
||||
startMark, endMark);
|
||||
error(root);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
|
|
@ -45,11 +45,13 @@ class ConstructorException : YAMLException
|
|||
*/
|
||||
this(string msg, Mark start, Mark end, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg ~ "\nstart:" ~ start.toString() ~ "\nend:" ~ end.toString(),
|
||||
super(msg ~ "\nstart: " ~ start.toString() ~ "\nend: " ~ end.toString(),
|
||||
file, line);
|
||||
}
|
||||
}
|
||||
|
||||
private alias ConstructorException Error;
|
||||
|
||||
/**
|
||||
* Constructs YAML values.
|
||||
*
|
||||
|
@ -177,8 +179,7 @@ final class Constructor
|
|||
if(is(T : string) || is(T == Node[]) || is(T == Node.Pair[]))
|
||||
{
|
||||
enforce((tag in *delegates!T) !is null,
|
||||
new ConstructorException("Could not determine a constructor for tag "
|
||||
~ tag.get(), start, end));
|
||||
new Error("No constructor function for tag " ~ tag.get(), start, end));
|
||||
Node node = Node(value);
|
||||
return Node.rawNode((*delegates!T)[tag](start, end, node), start, tag);
|
||||
}
|
||||
|
@ -234,7 +235,7 @@ bool constructBool(Mark start, Mark end, ref Node node)
|
|||
string value = node.get!string().toLower();
|
||||
if(["yes", "true", "on"].canFind(value)) {return true;}
|
||||
if(["no", "false", "off"].canFind(value)){return false;}
|
||||
throw new ConstructorException("Unable to parse boolean value: " ~ value, start, end);
|
||||
throw new Error("Unable to parse boolean value: " ~ value, start, end);
|
||||
}
|
||||
|
||||
///Construct an integer (long) node.
|
||||
|
@ -248,8 +249,7 @@ long constructLong(Mark start, Mark end, ref Node node)
|
|||
value = value[1 .. $];
|
||||
}
|
||||
|
||||
enforce(value != "", new ConstructorException("Unable to parse float value: " ~ value,
|
||||
start, end));
|
||||
enforce(value != "", new Error("Unable to parse float value: " ~ value, start, end));
|
||||
|
||||
long result;
|
||||
try
|
||||
|
@ -279,7 +279,7 @@ long constructLong(Mark start, Mark end, ref Node node)
|
|||
}
|
||||
catch(ConvException e)
|
||||
{
|
||||
throw new ConstructorException("Unable to parse integer value: " ~ value, start, end);
|
||||
throw new Error("Unable to parse integer value: " ~ value, start, end);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@ -318,7 +318,7 @@ real constructReal(Mark start, Mark end, ref Node node)
|
|||
}
|
||||
|
||||
enforce(value != "" && value != "nan" && value != "inf" && value != "-inf",
|
||||
new ConstructorException("Unable to parse float value: " ~ value, start, end));
|
||||
new Error("Unable to parse float value: " ~ value, start, end));
|
||||
|
||||
real result;
|
||||
try
|
||||
|
@ -344,7 +344,7 @@ real constructReal(Mark start, Mark end, ref Node node)
|
|||
}
|
||||
catch(ConvException e)
|
||||
{
|
||||
throw new ConstructorException("Unable to parse float value: " ~ value, start, end);
|
||||
throw new Error("Unable to parse float value: " ~ value, start, end);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@ -386,13 +386,13 @@ ubyte[] constructBinary(Mark start, Mark end, ref Node node)
|
|||
try{return Base64.decode(value.removechars("\n"));}
|
||||
catch(Exception e)
|
||||
{
|
||||
throw new ConstructorException("Unable to decode base64 value: " ~ e.msg, start,
|
||||
end);
|
||||
throw new Error("Unable to decode base64 value: " ~ e.msg,
|
||||
start, end);
|
||||
}
|
||||
}
|
||||
catch(UtfException e)
|
||||
{
|
||||
throw new ConstructorException("Unable to decode base64 value: " ~ e.msg, start, end);
|
||||
throw new Error("Unable to decode base64 value: " ~ e.msg, start, end);
|
||||
}
|
||||
}
|
||||
unittest
|
||||
|
@ -419,8 +419,8 @@ SysTime constructTimestamp(Mark start, Mark end, ref Node node)
|
|||
//First, get year, month and day.
|
||||
auto matches = match(value, YMDRegexp);
|
||||
|
||||
enforce(!matches.empty, new ConstructorException("Unable to parse timestamp value: "
|
||||
~ value, start, end));
|
||||
enforce(!matches.empty,
|
||||
new Error("Unable to parse timestamp value: " ~ value, start, end));
|
||||
|
||||
auto captures = matches.front.captures;
|
||||
const year = to!int(captures[1]);
|
||||
|
@ -467,13 +467,11 @@ SysTime constructTimestamp(Mark start, Mark end, ref Node node)
|
|||
}
|
||||
catch(ConvException e)
|
||||
{
|
||||
throw new ConstructorException("Unable to parse timestamp value: " ~ value ~
|
||||
" Reason: " ~ e.msg, start, end);
|
||||
throw new Error("Unable to parse timestamp value " ~ value ~ " : " ~ e.msg, start, end);
|
||||
}
|
||||
catch(DateTimeException e)
|
||||
{
|
||||
throw new ConstructorException("Invalid timestamp value: " ~ value ~
|
||||
" Reason: " ~ e.msg, start, end);
|
||||
throw new Error("Invalid timestamp value " ~ value ~ " : " ~ e.msg, start, end);
|
||||
}
|
||||
|
||||
assert(false, "This code should never be reached");
|
||||
|
@ -520,9 +518,8 @@ Node.Pair[] getPairs(string type, Mark start, Mark end, Node[] nodes)
|
|||
foreach(ref node; nodes)
|
||||
{
|
||||
enforce(node.isMapping && node.length == 1,
|
||||
new ConstructorException("While constructing " ~ type ~
|
||||
", expected a mapping with single element,", start,
|
||||
end));
|
||||
new Error("While constructing " ~ type ~
|
||||
", expected a mapping with single element", start, end));
|
||||
|
||||
pairs ~= node.get!(Node.Pair[]);
|
||||
}
|
||||
|
@ -542,8 +539,7 @@ Node.Pair[] constructOrderedMap(Mark start, Mark end, ref Node node)
|
|||
foreach(ref pair; pairs)
|
||||
{
|
||||
enforce((pair.key in map) is null,
|
||||
new ConstructorException("Found a duplicate entry in an ordered map",
|
||||
start, end));
|
||||
new Error("Duplicate entry in an ordered map", start, end));
|
||||
map[pair.key] = true;
|
||||
}
|
||||
clear(map);
|
||||
|
@ -611,7 +607,7 @@ Node[] constructSet(Mark start, Mark end, ref Node node)
|
|||
foreach(ref pair; pairs)
|
||||
{
|
||||
enforce((pair.key in map) is null,
|
||||
new ConstructorException("Found a duplicate entry in a set", start, end));
|
||||
new Error("Duplicate entry in a set", start, end));
|
||||
map[pair.key] = 0;
|
||||
nodes ~= pair.key;
|
||||
}
|
||||
|
@ -679,7 +675,7 @@ Node.Pair[] constructMap(Mark start, Mark end, ref Node node)
|
|||
foreach(ref pair; pairs)
|
||||
{
|
||||
enforce((pair.key in map) is null,
|
||||
new ConstructorException("Found a duplicate entry in a map", start, end));
|
||||
new Error("Duplicate entry in a map", start, end));
|
||||
map[pair.key] = true;
|
||||
}
|
||||
return pairs;
|
||||
|
|
|
@ -140,6 +140,9 @@ struct Dumper
|
|||
///Always write document end?
|
||||
bool explicitEnd_ = false;
|
||||
|
||||
///Name of the output file or stream, used in error messages.
|
||||
string name_ = "<unknown>";
|
||||
|
||||
public:
|
||||
@disable this();
|
||||
|
||||
|
@ -152,10 +155,12 @@ struct Dumper
|
|||
*/
|
||||
this(string filename)
|
||||
{
|
||||
name_ = filename;
|
||||
try{this(new File(filename, FileMode.OutNew));}
|
||||
catch(StreamException e)
|
||||
{
|
||||
throw new YAMLException("Unable to use file for YAML dumping " ~ filename ~ " : " ~ e.msg);
|
||||
throw new YAMLException("Unable to open file " ~ filename ~
|
||||
" for YAML dumping: " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -177,6 +182,12 @@ struct Dumper
|
|||
YAMLVersion_ = null;
|
||||
}
|
||||
|
||||
///Set stream _name. Used in debugging messages.
|
||||
@property void name(string name)
|
||||
{
|
||||
name_ = name;
|
||||
}
|
||||
|
||||
///Specify custom Resolver to use.
|
||||
void resolver(Resolver resolver)
|
||||
{
|
||||
|
@ -312,7 +323,8 @@ struct Dumper
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
throw new YAMLException("Unable to dump YAML: " ~ e.msg);
|
||||
throw new YAMLException("Unable to dump YAML to stream "
|
||||
~ name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -336,7 +348,8 @@ struct Dumper
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
throw new YAMLException("Unable to emit YAML: " ~ e.msg);
|
||||
throw new YAMLException("Unable to emit YAML to stream "
|
||||
~ name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -47,6 +47,8 @@ class EmitterException : YAMLException
|
|||
mixin ExceptionCtors;
|
||||
}
|
||||
|
||||
private alias EmitterException Error;
|
||||
|
||||
//Stores results of analysis of a scalar, determining e.g. what scalar style to use.
|
||||
align(4) struct ScalarAnalysis
|
||||
{
|
||||
|
@ -230,7 +232,7 @@ struct Emitter
|
|||
}
|
||||
catch(WriteException e)
|
||||
{
|
||||
throw new EmitterException("Unable to write to stream");
|
||||
throw new Error("Unable to write to stream: " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -293,7 +295,7 @@ struct Emitter
|
|||
bool eventTypeIs(in EventID id) const
|
||||
{
|
||||
enforce(!event_.isNull,
|
||||
new EmitterException("Expected an event, but no event is available."));
|
||||
new Error("Expected an event, but no event is available."));
|
||||
return event_.id == id;
|
||||
}
|
||||
|
||||
|
@ -307,8 +309,7 @@ struct Emitter
|
|||
void expectStreamStart()
|
||||
{
|
||||
enforce(eventTypeIs(EventID.StreamStart),
|
||||
new EmitterException("Expected StreamStart, but got "
|
||||
~ to!string(event_.id)));
|
||||
new Error("Expected StreamStart, but got " ~ event_.idString));
|
||||
|
||||
encoding_ = event_.encoding;
|
||||
writeStreamStart();
|
||||
|
@ -318,7 +319,7 @@ struct Emitter
|
|||
///Expect nothing, throwing if we still have something.
|
||||
void expectNothing()
|
||||
{
|
||||
throw new EmitterException("Expected nothing, but got " ~ to!string(event_.id));
|
||||
throw new Error("Expected nothing, but got " ~ event_.idString);
|
||||
}
|
||||
|
||||
//Document handlers.
|
||||
|
@ -327,8 +328,8 @@ struct Emitter
|
|||
void expectDocumentStart(bool first)()
|
||||
{
|
||||
enforce(eventTypeIs(EventID.DocumentStart) || eventTypeIs(EventID.StreamEnd),
|
||||
new EmitterException("Expected DocumentStart or StreamEnd, but got "
|
||||
~ to!string(event_.id)));
|
||||
new Error("Expected DocumentStart or StreamEnd, but got "
|
||||
~ event_.idString));
|
||||
|
||||
if(event_.id == EventID.DocumentStart)
|
||||
{
|
||||
|
@ -386,8 +387,7 @@ struct Emitter
|
|||
void expectDocumentEnd()
|
||||
{
|
||||
enforce(eventTypeIs(EventID.DocumentEnd),
|
||||
new EmitterException("Expected DocumentEnd, but got "
|
||||
~ to!string(event_.id)));
|
||||
new Error("Expected DocumentEnd, but got " ~ event_.idString));
|
||||
|
||||
writeIndent();
|
||||
if(event_.explicitDocument)
|
||||
|
@ -450,17 +450,15 @@ struct Emitter
|
|||
}
|
||||
break;
|
||||
default:
|
||||
throw new EmitterException("Expected Alias, Scalar, SequenceStart "
|
||||
"or MappingStart, but got: "
|
||||
~ to!string(event_.id));
|
||||
throw new Error("Expected Alias, Scalar, SequenceStart or "
|
||||
"MappingStart, but got: " ~ event_.idString);
|
||||
}
|
||||
}
|
||||
|
||||
///Handle an alias.
|
||||
void expectAlias()
|
||||
{
|
||||
enforce(!event_.anchor.isNull(),
|
||||
new EmitterException("Anchor is not specified for alias"));
|
||||
enforce(!event_.anchor.isNull(), new Error("Anchor is not specified for alias"));
|
||||
processAnchor("*");
|
||||
state_ = popState();
|
||||
}
|
||||
|
@ -785,7 +783,7 @@ struct Emitter
|
|||
return;
|
||||
}
|
||||
|
||||
enforce(!tag.isNull(), new EmitterException("Tag is not specified"));
|
||||
enforce(!tag.isNull(), new Error("Tag is not specified"));
|
||||
if(preparedTag_ is null){preparedTag_ = prepareTag(tag);}
|
||||
if(preparedTag_ !is null && preparedTag_ != "")
|
||||
{
|
||||
|
@ -841,7 +839,7 @@ struct Emitter
|
|||
static string prepareVersion(in string YAMLVersion)
|
||||
{
|
||||
enforce(YAMLVersion.split(".")[0] == "1",
|
||||
new EmitterException("Unsupported YAML version: " ~ YAMLVersion));
|
||||
new Error("Unsupported YAML version: " ~ YAMLVersion));
|
||||
return YAMLVersion;
|
||||
}
|
||||
|
||||
|
@ -861,13 +859,13 @@ struct Emitter
|
|||
static string prepareTagHandle(in string handle)
|
||||
{
|
||||
enforce(handle !is null && handle != "",
|
||||
new EmitterException("Tag handle must not be empty"));
|
||||
new Error("Tag handle must not be empty"));
|
||||
|
||||
if(handle.length > 1) foreach(const dchar c; handle[1 .. $ - 1])
|
||||
{
|
||||
enforce(isAlphaNum(c) || "-_".canFind(c),
|
||||
new EmitterException("Invalid character: " ~ to!string(c) ~
|
||||
" in tag handle " ~ handle));
|
||||
new Error("Invalid character: " ~ to!string(c) ~
|
||||
" in tag handle " ~ handle));
|
||||
}
|
||||
return handle;
|
||||
}
|
||||
|
@ -876,7 +874,7 @@ struct Emitter
|
|||
static string prepareTagPrefix(in string prefix)
|
||||
{
|
||||
enforce(prefix !is null && prefix != "",
|
||||
new EmitterException("Tag prefix must not be empty"));
|
||||
new Error("Tag prefix must not be empty"));
|
||||
|
||||
auto appender = appender!string();
|
||||
const offset = prefix[0] == '!' ? 1 : 0;
|
||||
|
@ -906,7 +904,7 @@ struct Emitter
|
|||
///Prepare tag for output.
|
||||
string prepareTag(in Tag tag)
|
||||
{
|
||||
enforce(!tag.isNull(), new EmitterException("Tag must not be empty"));
|
||||
enforce(!tag.isNull(), new Error("Tag must not be empty"));
|
||||
|
||||
string tagString = tag.get;
|
||||
if(tagString == "!"){return tagString;}
|
||||
|
@ -954,13 +952,12 @@ struct Emitter
|
|||
static string prepareAnchor(in Anchor anchor)
|
||||
{
|
||||
enforce(!anchor.isNull() && anchor.get != "",
|
||||
new EmitterException("Anchor must not be empty"));
|
||||
new Error("Anchor must not be empty"));
|
||||
const str = anchor.get;
|
||||
foreach(const dchar c; str)
|
||||
{
|
||||
enforce(isAlphaNum(c) || "-_".canFind(c),
|
||||
new EmitterException("Invalid character: " ~ to!string(c) ~
|
||||
" in anchor: " ~ str));
|
||||
new Error("Invalid character: " ~ to!string(c) ~ " in anchor: " ~ str));
|
||||
}
|
||||
return str;
|
||||
}
|
||||
|
@ -1150,8 +1147,7 @@ struct Emitter
|
|||
break;
|
||||
}
|
||||
|
||||
enforce(stream_.write(bom) == bom.length,
|
||||
new EmitterException("Unable to write to stream"));
|
||||
enforce(stream_.write(bom) == bom.length, new Error("Unable to write to stream"));
|
||||
}
|
||||
|
||||
///End the YAML stream.
|
||||
|
|
|
@ -83,6 +83,9 @@ struct Event
|
|||
{
|
||||
return id == EventID.Invalid;
|
||||
}
|
||||
|
||||
///Get string representation of the token ID.
|
||||
@property string idString() const {return to!string(id);}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -16,19 +16,11 @@ import std.string;
|
|||
///Base class for all exceptions thrown by D:YAML.
|
||||
class YAMLException : Exception
|
||||
{
|
||||
public:
|
||||
///Construct a YAMLException with specified message, and position where it was thrown.
|
||||
this(string msg, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg, file, line);
|
||||
}
|
||||
|
||||
package:
|
||||
//Set name of the file that was being processed when this exception was thrown.
|
||||
@property name(in string name)
|
||||
{
|
||||
msg = name ~ ":\n" ~ msg;
|
||||
}
|
||||
///Construct a YAMLException with specified message and position where it was thrown.
|
||||
public this(string msg, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg, file, line);
|
||||
}
|
||||
}
|
||||
|
||||
///Position in a YAML stream, used for error messages.
|
||||
|
@ -65,9 +57,9 @@ abstract class MarkedYAMLException : YAMLException
|
|||
this(string context, Mark contextMark, string problem, Mark problemMark,
|
||||
string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
string msg = context ~ '\n';
|
||||
if(contextMark != problemMark){msg ~= contextMark.toString() ~ '\n';}
|
||||
msg ~= problem ~ '\n' ~ problemMark.toString() ~ '\n';
|
||||
const msg = context ~ '\n' ~
|
||||
(contextMark != problemMark ? contextMark.toString() ~ '\n' : "") ~
|
||||
problem ~ '\n' ~ problemMark.toString() ~ '\n';
|
||||
super(msg, file, line);
|
||||
}
|
||||
|
||||
|
@ -81,11 +73,10 @@ abstract class MarkedYAMLException : YAMLException
|
|||
//Constructors of YAML exceptions are mostly the same, so we use a mixin.
|
||||
template ExceptionCtors()
|
||||
{
|
||||
public:
|
||||
this(string msg, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg, file, line);
|
||||
}
|
||||
public this(string msg, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg, file, line);
|
||||
}
|
||||
}
|
||||
|
||||
//Constructors of marked YAML exceptions are mostly the same, so we use a mixin.
|
||||
|
|
|
@ -104,23 +104,23 @@ struct Loader
|
|||
string name_ = "<unknown>";
|
||||
|
||||
public:
|
||||
@disable this();
|
||||
|
||||
/**
|
||||
* Construct a Loader to load YAML from a file.
|
||||
*
|
||||
* Params: filename = Name of the file to load from.
|
||||
*
|
||||
* Throws: YAMLException if the file could not be opened or read from.
|
||||
* Throws: YAMLException if the file could not be opened or read.
|
||||
*/
|
||||
this(in string filename)
|
||||
{
|
||||
try
|
||||
{
|
||||
name = filename;
|
||||
this(new File(filename));
|
||||
}
|
||||
name_ = filename;
|
||||
try{this(new File(filename));}
|
||||
catch(StreamException e)
|
||||
{
|
||||
throw new YAMLException("Unable to load YAML file " ~ filename ~ " : " ~ e.msg);
|
||||
throw new YAMLException("Unable to open file " ~ filename ~
|
||||
" for YAML loading: " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -129,7 +129,7 @@ struct Loader
|
|||
*
|
||||
* Params: stream = Stream to read from. Must be readable.
|
||||
*
|
||||
* Throws: YAMLException if stream could not be read from.
|
||||
* Throws: YAMLException if stream could not be read.
|
||||
*/
|
||||
this(Stream stream)
|
||||
{
|
||||
|
@ -145,8 +145,8 @@ struct Loader
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
e.name = name_;
|
||||
throw e;
|
||||
throw new YAMLException("Unable to open stream " ~ name_ ~
|
||||
" for YAML loading: " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -181,7 +181,7 @@ struct Loader
|
|||
/**
|
||||
* Load single YAML document.
|
||||
*
|
||||
* If none or more than one YAML document is found, this will throw a YAMLException.
|
||||
* If none or more than one YAML document is found, this throws a YAMLException.
|
||||
*
|
||||
* Returns: Root node of the document.
|
||||
*
|
||||
|
@ -198,8 +198,8 @@ struct Loader
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
e.name = name_;
|
||||
throw e;
|
||||
throw new YAMLException("Unable to load YAML from stream " ~
|
||||
name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -208,15 +208,12 @@ struct Loader
|
|||
*
|
||||
* Returns: Array of root nodes of all documents in the file/stream.
|
||||
*
|
||||
* Throws: YAMLException on a YAML parsing error.
|
||||
* Throws: YAMLException on a parsing error.
|
||||
*/
|
||||
Node[] loadAll()
|
||||
{
|
||||
Node[] nodes;
|
||||
foreach(ref node; this)
|
||||
{
|
||||
nodes ~= node;
|
||||
}
|
||||
foreach(ref node; this){nodes ~= node;}
|
||||
return nodes;
|
||||
}
|
||||
|
||||
|
@ -245,8 +242,8 @@ struct Loader
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
e.name = name_;
|
||||
throw e;
|
||||
throw new YAMLException("Unable to load YAML from stream " ~
|
||||
name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -262,8 +259,8 @@ struct Loader
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
e.name = name_;
|
||||
throw e;
|
||||
throw new YAMLException("Unable to scan YAML from stream " ~
|
||||
name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -278,8 +275,8 @@ struct Loader
|
|||
}
|
||||
catch(YAMLException e)
|
||||
{
|
||||
e.name = name_;
|
||||
throw e;
|
||||
throw new YAMLException("Unable to parse YAML from stream " ~
|
||||
name_ ~ " : " ~ e.msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
59
dyaml/node.d
59
dyaml/node.d
|
@ -39,10 +39,12 @@ class NodeException : YAMLException
|
|||
*/
|
||||
this(string msg, Mark start, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super(msg ~ "\nNode at:" ~ start.toString(), file, line);
|
||||
super(msg ~ "\nNode at: " ~ start.toString(), file, line);
|
||||
}
|
||||
}
|
||||
|
||||
private alias NodeException Error;
|
||||
|
||||
//Node kinds.
|
||||
package enum NodeID : ubyte
|
||||
{
|
||||
|
@ -532,8 +534,8 @@ struct Node
|
|||
void throwUnexpectedType()
|
||||
{
|
||||
//Can't get the value.
|
||||
throw new NodeException("Node has unexpected type " ~ type.toString ~
|
||||
". Expected " ~ typeid(T).toString, startMark_);
|
||||
throw new Error("Node has unexpected type: " ~ type.toString ~
|
||||
". Expected: " ~ typeid(T).toString, startMark_);
|
||||
}
|
||||
|
||||
static if(isSomeString!T)
|
||||
|
@ -546,8 +548,7 @@ struct Node
|
|||
}
|
||||
catch(VariantException e)
|
||||
{
|
||||
throw new NodeException("Unable to convert node value to a string",
|
||||
startMark_);
|
||||
throw new Error("Unable to convert node value to string", startMark_);
|
||||
}
|
||||
}
|
||||
else static if(isFloatingPoint!T)
|
||||
|
@ -571,9 +572,9 @@ struct Node
|
|||
long temp = value_.get!long;
|
||||
if(temp < T.min || temp > T.max)
|
||||
{
|
||||
throw new NodeException("Integer value out of range of type " ~
|
||||
typeid(T).toString ~ "Value: " ~
|
||||
to!string(temp), startMark_);
|
||||
throw new Error("Integer value out of range of type " ~
|
||||
typeid(T).toString ~ "Value: " ~ to!string(temp),
|
||||
startMark_);
|
||||
}
|
||||
target = to!T(temp);
|
||||
return;
|
||||
|
@ -602,8 +603,7 @@ struct Node
|
|||
{
|
||||
if(isSequence) {return get!(Node[]).length;}
|
||||
else if(isMapping){return get!(Pair[]).length;}
|
||||
throw new NodeException("Trying to get length of a node that is not a collection",
|
||||
startMark_);
|
||||
throw new Error("Trying to get length of a scalar node", startMark_);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -637,12 +637,10 @@ struct Node
|
|||
auto idx = findPair(index);
|
||||
if(idx >= 0){return get!(Pair[])[idx].value;}
|
||||
|
||||
throw new NodeException("Mapping index not found" ~
|
||||
isSomeString!T ? ": " ~ to!string(index) : "",
|
||||
startMark_);
|
||||
throw new Error("Mapping index not found" ~
|
||||
isSomeString!T ? ": " ~ to!string(index) : "", startMark_);
|
||||
}
|
||||
throw new NodeException("Trying to index node that does not support indexing",
|
||||
startMark_);
|
||||
throw new Error("Trying to index node that does not support indexing", startMark_);
|
||||
}
|
||||
unittest
|
||||
{
|
||||
|
@ -723,8 +721,7 @@ struct Node
|
|||
return;
|
||||
}
|
||||
|
||||
throw new NodeException("Trying to index a YAML node that is not a collection.",
|
||||
startMark_);
|
||||
throw new Error("Trying to index a scalar node.", startMark_);
|
||||
}
|
||||
unittest
|
||||
{
|
||||
|
@ -758,8 +755,8 @@ struct Node
|
|||
int opApply(T)(int delegate(ref T) dg)
|
||||
{
|
||||
enforce(isSequence,
|
||||
new NodeException("Trying to iterate over a node that is not a sequence",
|
||||
startMark_));
|
||||
new Error("Trying to iterate over a node that is not a sequence",
|
||||
startMark_));
|
||||
|
||||
int result = 0;
|
||||
foreach(ref node; get!(Node[]))
|
||||
|
@ -815,8 +812,8 @@ struct Node
|
|||
int opApply(K, V)(int delegate(ref K, ref V) dg)
|
||||
{
|
||||
enforce(isMapping,
|
||||
new NodeException("Trying to iterate over a node that is not a mapping",
|
||||
startMark_));
|
||||
new Error("Trying to iterate over a node that is not a mapping",
|
||||
startMark_));
|
||||
|
||||
int result = 0;
|
||||
foreach(ref pair; get!(Node.Pair[]))
|
||||
|
@ -915,8 +912,7 @@ struct Node
|
|||
void add(T)(T value)
|
||||
{
|
||||
enforce(isSequence(),
|
||||
new NodeException("Trying to add an element to a "
|
||||
"non-sequence YAML node", startMark_));
|
||||
new Error("Trying to add an element to a non-sequence node", startMark_));
|
||||
|
||||
auto nodes = get!(Node[])();
|
||||
static if(is(T == Node)){nodes ~= value;}
|
||||
|
@ -953,8 +949,8 @@ struct Node
|
|||
void add(K, V)(K key, V value)
|
||||
{
|
||||
enforce(isMapping(),
|
||||
new NodeException("Trying to add a key-value pair to a "
|
||||
"non-mapping YAML node", startMark_));
|
||||
new Error("Trying to add a key-value pair to a non-mapping node",
|
||||
startMark_));
|
||||
|
||||
auto pairs = get!(Node.Pair[])();
|
||||
pairs ~= Pair(key, value);
|
||||
|
@ -1010,8 +1006,7 @@ struct Node
|
|||
}
|
||||
return;
|
||||
}
|
||||
throw new NodeException("Trying to remove an element from a YAML node that "
|
||||
"is not a collection.", startMark_);
|
||||
throw new Error("Trying to remove an element from a scalar node", startMark_);
|
||||
}
|
||||
unittest
|
||||
{
|
||||
|
@ -1077,8 +1072,7 @@ struct Node
|
|||
}
|
||||
return;
|
||||
}
|
||||
throw new NodeException("Trying to remove an element from a YAML node that "
|
||||
"is not a collection.", startMark_);
|
||||
throw new Error("Trying to remove an element from a scalar node", startMark_);
|
||||
}
|
||||
unittest
|
||||
{
|
||||
|
@ -1334,14 +1328,13 @@ struct Node
|
|||
{
|
||||
static if(!isIntegral!T)
|
||||
{
|
||||
throw new NodeException("Indexing a YAML sequence with a non-integral type.",
|
||||
startMark_);
|
||||
throw new Error("Indexing a sequence with a non-integral type.", startMark_);
|
||||
}
|
||||
else
|
||||
{
|
||||
enforce(index >= 0 && index < value_.get!(Node[]).length,
|
||||
new NodeException("Index to a YAML sequence out of range: "
|
||||
~ to!string(index), startMark_));
|
||||
new Error("Sequence index out of range: " ~ to!string(index),
|
||||
startMark_));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -99,6 +99,8 @@ class ParserException : MarkedYAMLException
|
|||
mixin MarkedExceptionCtors;
|
||||
}
|
||||
|
||||
private alias ParserException Error;
|
||||
|
||||
///Generates events from tokens provided by a Scanner.
|
||||
final class Parser
|
||||
{
|
||||
|
@ -225,7 +227,7 @@ final class Parser
|
|||
Event delegate() popState()
|
||||
{
|
||||
enforce(states_.length > 0,
|
||||
new YAMLException("Parser: Need to pop a state but there are no states left"));
|
||||
new YAMLException("Parser: Need to pop state but no states left to pop"));
|
||||
const result = states_.back();
|
||||
states_.popBack;
|
||||
return result;
|
||||
|
@ -235,7 +237,7 @@ final class Parser
|
|||
Mark popMark()
|
||||
{
|
||||
enforce(marks_.length > 0,
|
||||
new YAMLException("Parser: Need to pop a mark but there are no marks left"));
|
||||
new YAMLException("Parser: Need to pop mark but no marks left to pop"));
|
||||
const result = marks_.back();
|
||||
marks_.popBack;
|
||||
return result;
|
||||
|
@ -286,9 +288,9 @@ final class Parser
|
|||
|
||||
auto tagDirectives = processDirectives();
|
||||
enforce(scanner_.checkToken(TokenID.DocumentStart),
|
||||
new ParserException("Expected document start but found " ~
|
||||
to!string(scanner_.peekToken().id),
|
||||
scanner_.peekToken().startMark));
|
||||
new Error("Expected document start but found " ~
|
||||
scanner_.peekToken().idString,
|
||||
scanner_.peekToken().startMark));
|
||||
|
||||
const endMark = scanner_.getToken().endMark;
|
||||
states_ ~= &parseDocumentEnd;
|
||||
|
@ -347,12 +349,11 @@ final class Parser
|
|||
if(name == "YAML")
|
||||
{
|
||||
enforce(YAMLVersion_ is null,
|
||||
new ParserException("Found duplicate YAML directive",
|
||||
token.startMark));
|
||||
new Error("Duplicate YAML directive", token.startMark));
|
||||
const minor = parts[1].split(".")[0];
|
||||
enforce(to!int(minor) == 1,
|
||||
new ParserException("Found incompatible YAML document (version "
|
||||
"1.* is required)", token.startMark));
|
||||
new Error("Incompatible document (version 1.x is required)",
|
||||
token.startMark));
|
||||
YAMLVersion_ = parts[1];
|
||||
}
|
||||
else if(name == "TAG")
|
||||
|
@ -365,8 +366,8 @@ final class Parser
|
|||
//handle
|
||||
auto h = pair[0];
|
||||
auto replacement = pair[1];
|
||||
enforce(h != handle, new ParserException("Duplicate tag handle: " ~
|
||||
handle, token.startMark));
|
||||
enforce(h != handle, new Error("Duplicate tag handle: " ~ handle,
|
||||
token.startMark));
|
||||
}
|
||||
tagHandles_ ~= tuple(handle, parts[2]);
|
||||
}
|
||||
|
@ -515,9 +516,9 @@ final class Parser
|
|||
}
|
||||
|
||||
Token token = scanner_.peekToken();
|
||||
throw new ParserException("While parsing a " ~ (block ? "block" : "flow") ~ " node",
|
||||
startMark, "expected the node content, but found: "
|
||||
~ to!string(token.id), token.startMark);
|
||||
throw new Error("While parsing a " ~ (block ? "block" : "flow") ~ " node",
|
||||
startMark, "expected the node content, but found: "
|
||||
~ token.idString, token.startMark);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -549,8 +550,8 @@ final class Parser
|
|||
}
|
||||
//handle must be in tagHandles_
|
||||
enforce(replacement !is null,
|
||||
new ParserException("While parsing a node", startMark,
|
||||
"found undefined tag handle: " ~ handle, tagMark));
|
||||
new Error("While parsing a node", startMark,
|
||||
"found undefined tag handle: " ~ handle, tagMark));
|
||||
return replacement ~ suffix;
|
||||
}
|
||||
return suffix;
|
||||
|
@ -584,9 +585,9 @@ final class Parser
|
|||
if(!scanner_.checkToken(TokenID.BlockEnd))
|
||||
{
|
||||
Token token = scanner_.peekToken();
|
||||
throw new ParserException("While parsing a block collection", marks_[$ - 1],
|
||||
"expected block end, but found "
|
||||
~ to!string(token.id), token.startMark);
|
||||
throw new Error("While parsing a block collection", marks_[$ - 1],
|
||||
"expected block end, but found " ~ token.idString,
|
||||
token.startMark);
|
||||
}
|
||||
|
||||
state_ = popState();
|
||||
|
@ -649,9 +650,9 @@ final class Parser
|
|||
if(!scanner_.checkToken(TokenID.BlockEnd))
|
||||
{
|
||||
Token token = scanner_.peekToken();
|
||||
throw new ParserException("While parsing a block mapping", marks_[$ - 1],
|
||||
"expected block end, but found: "
|
||||
~ to!string(token.id), token.startMark);
|
||||
throw new Error("While parsing a block mapping", marks_[$ - 1],
|
||||
"expected block end, but found: " ~ token.idString,
|
||||
token.startMark);
|
||||
}
|
||||
|
||||
state_ = popState();
|
||||
|
@ -710,10 +711,9 @@ final class Parser
|
|||
else
|
||||
{
|
||||
Token token = scanner_.peekToken;
|
||||
throw new ParserException("While parsing a flow sequence",
|
||||
marks_[$ - 1],
|
||||
"expected ',' or ']', but got: " ~
|
||||
to!string(token.id), token.startMark);
|
||||
throw new Error("While parsing a flow sequence", marks_[$ - 1],
|
||||
"expected ',' or ']', but got: " ~
|
||||
token.idString, token.startMark);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -818,10 +818,9 @@ final class Parser
|
|||
else
|
||||
{
|
||||
Token token = scanner_.peekToken;
|
||||
throw new ParserException("While parsing a flow mapping",
|
||||
marks_[$ - 1],
|
||||
"expected ',' or '}', but got: " ~
|
||||
to!string(token.id), token.startMark);
|
||||
throw new Error("While parsing a flow mapping", marks_[$ - 1],
|
||||
"expected ',' or '}', but got: " ~
|
||||
token.idString, token.startMark);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -29,7 +29,7 @@ class ReaderException : YAMLException
|
|||
{
|
||||
this(string msg, string file = __FILE__, int line = __LINE__)
|
||||
{
|
||||
super("Error reading YAML stream: " ~ msg, file, line);
|
||||
super("Error reading stream: " ~ msg, file, line);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -105,11 +105,11 @@ final class Reader
|
|||
rawBuffer16_[0] = stream_.getcw();
|
||||
rawUsed_ = 1;
|
||||
enforce(stream_.available % 2 == 0,
|
||||
new ReaderException("Odd number of bytes in an UTF-16 stream"));
|
||||
new ReaderException("Odd byte count in an UTF-16 stream"));
|
||||
break;
|
||||
case 3, 4:
|
||||
enforce(stream_.available % 4 == 0,
|
||||
new ReaderException("Number of bytes in an UTF-32 stream not divisible by 4"));
|
||||
new ReaderException("Byte count in an UTF-32 stream not divisible by 4"));
|
||||
encoding_ = Encoding.UTF_32;
|
||||
break;
|
||||
default: assert(false, "Unknown UTF BOM");
|
||||
|
@ -286,7 +286,7 @@ final class Reader
|
|||
*
|
||||
* Params: chars = Maximum number of characters to load.
|
||||
*
|
||||
* Throws: ReaderException on unicode decoding error,
|
||||
* Throws: ReaderException on Unicode decoding error,
|
||||
* if nonprintable characters are detected, or
|
||||
* if there is an error reading from the stream.
|
||||
*/
|
||||
|
@ -382,13 +382,12 @@ final class Reader
|
|||
catch(UtfException e)
|
||||
{
|
||||
const position = stream_.position;
|
||||
throw new ReaderException("Unicode decoding error between bytes " ~
|
||||
to!string(oldPosition) ~ " and " ~
|
||||
to!string(position) ~ " " ~ e.msg);
|
||||
throw new ReaderException(format("Unicode decoding error between bytes ",
|
||||
oldPosition, " and ", position, " : ", e.msg));
|
||||
}
|
||||
catch(ReadException e)
|
||||
{
|
||||
throw new ReaderException("Error reading from the stream: " ~ e.msg);
|
||||
throw new ReaderException(e.msg);
|
||||
}
|
||||
|
||||
enforce(printable(buffer_[oldLength .. $]),
|
||||
|
|
|
@ -73,12 +73,12 @@ final class Representer
|
|||
/**
|
||||
* Add a function to represent nodes with a specific data type.
|
||||
*
|
||||
* The representer function takes a reference to a Node storing the data
|
||||
* The representer function takes references to a Node storing the data
|
||||
* type and to the Representer. It returns the represented node and may
|
||||
* throw a RepresenterException. See the example for more information.
|
||||
*
|
||||
* Only one function may be specified for one data type. Default data
|
||||
* types already have representer functions unless disabled in these
|
||||
* types already have representer functions unless disabled in the
|
||||
* Representer constructor.
|
||||
*
|
||||
* Params: representer = Representer function to add.
|
||||
|
@ -297,8 +297,8 @@ final class Representer
|
|||
auto type = data.isUserType ? data.get!YAMLObject.type : data.type;
|
||||
|
||||
enforce((type in representers_) !is null,
|
||||
new RepresenterException("No YAML representer function for type "
|
||||
~ type.toString() ~ " cannot represent."));
|
||||
new RepresenterException("No representer function for type "
|
||||
~ type.toString() ~ " , cannot represent."));
|
||||
Node result = representers_[type](data, this);
|
||||
if(!data.tag.isNull()){result.tag = data.tag;}
|
||||
return result;
|
||||
|
@ -426,8 +426,7 @@ Node representPairs(ref Node node, Representer representer)
|
|||
if(node.tag == Tag("tag:yaml.org,2002:omap"))
|
||||
{
|
||||
enforce(!hasDuplicates(pairs),
|
||||
new RepresenterException("Found a duplicate entry "
|
||||
"in an ordered map"));
|
||||
new RepresenterException("Duplicate entry in an ordered map"));
|
||||
return representer.representSequence(node.tag.get, mapToSequence(pairs));
|
||||
}
|
||||
else if(node.tag == Tag("tag:yaml.org,2002:pairs"))
|
||||
|
@ -437,8 +436,7 @@ Node representPairs(ref Node node, Representer representer)
|
|||
else
|
||||
{
|
||||
enforce(!hasDuplicates(pairs),
|
||||
new RepresenterException("Found a duplicate entry "
|
||||
"in an unordered map"));
|
||||
new RepresenterException("Duplicate entry in an unordered map"));
|
||||
return representer.representMapping("tag:yaml.org,2002:map", pairs);
|
||||
}
|
||||
}
|
||||
|
|
162
dyaml/scanner.d
162
dyaml/scanner.d
|
@ -63,6 +63,8 @@ class ScannerException : MarkedYAMLException
|
|||
mixin MarkedExceptionCtors;
|
||||
}
|
||||
|
||||
private alias ScannerException Error;
|
||||
|
||||
///Generates tokens from data provided by a Reader.
|
||||
final class Scanner
|
||||
{
|
||||
|
@ -269,9 +271,9 @@ final class Scanner
|
|||
if(c == '\"') {return fetchDouble();}
|
||||
if(checkPlain()) {return fetchPlain();}
|
||||
|
||||
throw new ScannerException(format("While scanning for the next token, found "
|
||||
"character \'", c, "\', index ",to!int(c),
|
||||
" that cannot start " "any token"), reader_.mark);
|
||||
throw new Error(format("While scanning for the next token, found "
|
||||
"character \'", c, "\', index ",to!int(c),
|
||||
" that cannot start any token"), reader_.mark);
|
||||
}
|
||||
|
||||
|
||||
|
@ -303,9 +305,9 @@ final class Scanner
|
|||
if(key.line != reader_.line || reader_.charIndex - key.charIndex > 1024)
|
||||
{
|
||||
enforce(!key.required,
|
||||
new ScannerException("While scanning a simple key",
|
||||
Mark(key.line, key.column),
|
||||
"could not find expected ':'", reader_.mark));
|
||||
new Error("While scanning a simple key",
|
||||
Mark(key.line, key.column),
|
||||
"could not find expected ':'", reader_.mark));
|
||||
levelsToRemove ~= level;
|
||||
}
|
||||
}
|
||||
|
@ -341,10 +343,8 @@ final class Scanner
|
|||
{
|
||||
auto key = possibleSimpleKeys_[flowLevel_];
|
||||
enforce(!key.required,
|
||||
new ScannerException("While scanning a simple key",
|
||||
Mark(key.line, key.column),
|
||||
"could not find expected ':'",
|
||||
reader_.mark));
|
||||
new Error("While scanning a simple key", Mark(key.line, key.column),
|
||||
"could not find expected ':'", reader_.mark));
|
||||
possibleSimpleKeys_.remove(flowLevel_);
|
||||
}
|
||||
}
|
||||
|
@ -369,8 +369,8 @@ final class Scanner
|
|||
//restrictive than what the specification requires.
|
||||
//if(pedantic_ && flowLevel_ > 0 && indent_ > column)
|
||||
//{
|
||||
// throw new ScannerException("Invalid intendation or unclosed '[' or '{'",
|
||||
// reader_.mark)
|
||||
// throw new Error("Invalid intendation or unclosed '[' or '{'",
|
||||
// reader_.mark)
|
||||
//}
|
||||
return;
|
||||
}
|
||||
|
@ -510,8 +510,8 @@ final class Scanner
|
|||
void blockChecks(string type, TokenID id)()
|
||||
{
|
||||
//Are we allowed to start a key (not neccesarily a simple one)?
|
||||
enforce(allowSimpleKey_, new ScannerException(type ~ " keys are not allowed here",
|
||||
reader_.mark));
|
||||
enforce(allowSimpleKey_, new Error(type ~ " keys are not allowed here",
|
||||
reader_.mark));
|
||||
|
||||
if(addIndent(reader_.column))
|
||||
{
|
||||
|
@ -585,8 +585,7 @@ final class Scanner
|
|||
{
|
||||
//We can start a complex value if and only if we can start a simple key.
|
||||
enforce(flowLevel_ > 0 || allowSimpleKey_,
|
||||
new ScannerException("Mapping values are not allowed here",
|
||||
reader_.mark));
|
||||
new Error("Mapping values are not allowed here", reader_.mark));
|
||||
|
||||
//If this value starts a new block mapping, we need to add
|
||||
//BLOCK-MAPPING-START. It'll be detected as an error later by the parser.
|
||||
|
@ -777,9 +776,9 @@ final class Scanner
|
|||
}
|
||||
|
||||
enforce(length > 0,
|
||||
new ScannerException("While scanning " ~ name, startMark,
|
||||
"expected alphanumeric, - or _, but found "
|
||||
~ to!string(c), reader_.mark));
|
||||
new Error("While scanning " ~ name, startMark,
|
||||
"expected alphanumeric, - or _, but found " ~ to!string(c),
|
||||
reader_.mark));
|
||||
|
||||
return reader_.get(length);
|
||||
}
|
||||
|
@ -856,9 +855,9 @@ final class Scanner
|
|||
const name = scanAlphaNumeric!"a directive"(startMark);
|
||||
|
||||
enforce(" \0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a directive", startMark,
|
||||
"expected alphanumeric, - or _, but found "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive", startMark,
|
||||
"expected alphanumeric, - or _, but found "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
return name;
|
||||
}
|
||||
|
||||
|
@ -869,17 +868,17 @@ final class Scanner
|
|||
|
||||
dstring result = scanYAMLDirectiveNumber(startMark);
|
||||
enforce(reader_.peek() == '.',
|
||||
new ScannerException("While scanning a directive", startMark,
|
||||
"expected a digit or '.', but found: "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive", startMark,
|
||||
"expected a digit or '.', but found: "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
//Skip the '.'.
|
||||
reader_.forward();
|
||||
|
||||
result ~= '.' ~ scanYAMLDirectiveNumber(startMark);
|
||||
enforce(" \0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a directive", startMark,
|
||||
"expected a digit or '.', but found: "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive", startMark,
|
||||
"expected a digit or '.', but found: "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -887,9 +886,9 @@ final class Scanner
|
|||
dstring scanYAMLDirectiveNumber(in Mark startMark)
|
||||
{
|
||||
enforce(isDigit(reader_.peek()),
|
||||
new ScannerException("While scanning a directive", startMark,
|
||||
"expected a digit, but found: " ~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive", startMark,
|
||||
"expected a digit, but found: " ~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
|
||||
//Already found the first digit in the enforce(), so set length to 1.
|
||||
uint length = 1;
|
||||
|
@ -912,9 +911,9 @@ final class Scanner
|
|||
{
|
||||
const value = scanTagHandle("directive", startMark);
|
||||
enforce(reader_.peek() == ' ',
|
||||
new ScannerException("While scanning a directive handle", startMark,
|
||||
"expected ' ', but found: " ~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive handle", startMark,
|
||||
"expected ' ', but found: " ~ to!string(reader_.peek()),
|
||||
reader_.mark));
|
||||
return value;
|
||||
}
|
||||
|
||||
|
@ -923,9 +922,9 @@ final class Scanner
|
|||
{
|
||||
const value = scanTagURI("directive", startMark);
|
||||
enforce(" \0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a directive prefix", startMark,
|
||||
"expected ' ', but found" ~ to!string(reader_.peek()),
|
||||
reader_.mark));
|
||||
new Error("While scanning a directive prefix", startMark,
|
||||
"expected ' ', but found" ~ to!string(reader_.peek()),
|
||||
reader_.mark));
|
||||
|
||||
return value;
|
||||
}
|
||||
|
@ -936,9 +935,9 @@ final class Scanner
|
|||
findNextNonSpace();
|
||||
if(reader_.peek() == '#'){scanToNextBreak();}
|
||||
enforce("\0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a directive", startMark,
|
||||
"expected comment or a line break, but found"
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a directive", startMark,
|
||||
"expected comment or a line break, but found"
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
scanLineBreak();
|
||||
}
|
||||
|
||||
|
@ -966,7 +965,7 @@ final class Scanner
|
|||
|
||||
enforce((" \t\0\n\r\u0085\u2028\u2029".canFind(reader_.peek()) ||
|
||||
("?:,]}%@").canFind(reader_.peek())),
|
||||
new ScannerException("While scanning an " ~ (i == '*') ? "alias" : "anchor",
|
||||
new Error("While scanning an " ~ (i == '*') ? "alias" : "anchor",
|
||||
startMark, "expected alphanumeric, - or _, but found "~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
|
||||
|
@ -994,9 +993,9 @@ final class Scanner
|
|||
reader_.forward(2);
|
||||
suffix = scanTagURI("tag", startMark);
|
||||
enforce(reader_.peek() == '>',
|
||||
new ScannerException("While scanning a tag", startMark,
|
||||
"expected '>' but found" ~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a tag", startMark,
|
||||
"expected '>' but found" ~ to!string(reader_.peek()),
|
||||
reader_.mark));
|
||||
reader_.forward();
|
||||
}
|
||||
else if(" \t\0\n\r\u0085\u2028\u2029".canFind(c))
|
||||
|
@ -1031,9 +1030,9 @@ final class Scanner
|
|||
}
|
||||
|
||||
enforce(" \0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a tag", startMark,
|
||||
"expected ' ' but found" ~
|
||||
to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a tag", startMark,
|
||||
"expected ' ' but found" ~ to!string(reader_.peek()),
|
||||
reader_.mark));
|
||||
return tagToken(startMark, reader_.mark, to!string(handle ~ '\0' ~ suffix));
|
||||
}
|
||||
|
||||
|
@ -1141,9 +1140,9 @@ final class Scanner
|
|||
if(!isDigit(c)){return false;}
|
||||
increment = to!int(""d ~ c);
|
||||
enforce(increment != 0,
|
||||
new ScannerException("While scanning a block scalar", startMark,
|
||||
"expected indentation indicator in range 1-9, "
|
||||
"but found 0", reader_.mark));
|
||||
new Error("While scanning a block scalar", startMark,
|
||||
"expected indentation indicator in range 1-9, but found 0",
|
||||
reader_.mark));
|
||||
reader_.forward();
|
||||
c = reader_.peek();
|
||||
return true;
|
||||
|
@ -1154,9 +1153,9 @@ final class Scanner
|
|||
else if(getIncrement()){getChomping();}
|
||||
|
||||
enforce(" \0\n\r\u0085\u2028\u2029".canFind(c),
|
||||
new ScannerException("While scanning a block scalar", startMark,
|
||||
"expected chomping or indentation indicator, "
|
||||
"but found " ~ to!string(c), reader_.mark));
|
||||
new Error("While scanning a block scalar", startMark,
|
||||
"expected chomping or indentation indicator, but found "
|
||||
~ to!string(c), reader_.mark));
|
||||
|
||||
return tuple(chomping, increment);
|
||||
}
|
||||
|
@ -1168,9 +1167,9 @@ final class Scanner
|
|||
if(reader_.peek == '#'){scanToNextBreak();}
|
||||
|
||||
enforce("\0\n\r\u0085\u2028\u2029".canFind(reader_.peek()),
|
||||
new ScannerException("While scanning a block scalar", startMark,
|
||||
"expected a comment or a line break, but found "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
new Error("While scanning a block scalar", startMark,
|
||||
"expected a comment or a line break, but found "
|
||||
~ to!string(reader_.peek()), reader_.mark));
|
||||
scanLineBreak();
|
||||
}
|
||||
|
||||
|
@ -1300,7 +1299,7 @@ final class Scanner
|
|||
foreach(i; 0 .. length)
|
||||
{
|
||||
enforce(isHexDigit(reader_.peek(i)),
|
||||
new ScannerException(
|
||||
new Error(
|
||||
"While scanning a double qouted scalar", startMark,
|
||||
"expected escape sequence of " ~ to!string(length) ~
|
||||
" hexadecimal numbers, but found " ~
|
||||
|
@ -1317,7 +1316,7 @@ final class Scanner
|
|||
}
|
||||
else
|
||||
{
|
||||
throw new ScannerException("While scanning a double quoted scalar",
|
||||
throw new Error("While scanning a double quoted scalar",
|
||||
startMark,
|
||||
"found unknown escape character: " ~
|
||||
to!string(c), reader_.mark);
|
||||
|
@ -1336,8 +1335,8 @@ final class Scanner
|
|||
|
||||
dchar c = reader_.peek();
|
||||
enforce(c != '\0',
|
||||
new ScannerException("While scanning a quoted scalar", startMark,
|
||||
"found unexpected end of stream", reader_.mark));
|
||||
new Error("While scanning a quoted scalar", startMark,
|
||||
"found unexpected end of stream", reader_.mark));
|
||||
|
||||
auto appender = appender!dstring();
|
||||
if("\n\r\u0085\u2028\u2029".canFind(c))
|
||||
|
@ -1364,9 +1363,8 @@ final class Scanner
|
|||
if((prefix == "---" || prefix == "...") &&
|
||||
" \t\0\n\r\u0085\u2028\u2029".canFind(reader_.peek(3)))
|
||||
{
|
||||
throw new ScannerException("While scanning a quoted scalar", startMark,
|
||||
"found unexpected document separator",
|
||||
reader_.mark);
|
||||
throw new Error("While scanning a quoted scalar", startMark,
|
||||
"found unexpected document separator", reader_.mark);
|
||||
}
|
||||
|
||||
while(" \t".canFind(reader_.peek())){reader_.forward();}
|
||||
|
@ -1417,10 +1415,10 @@ final class Scanner
|
|||
!",[]{}".canFind(reader_.peek(length + 1)))
|
||||
{
|
||||
reader_.forward(length);
|
||||
throw new ScannerException("While scanning a plain scalar", startMark,
|
||||
"found unexpected ':' . Please check "
|
||||
"http://pyyaml.org/wiki/YAMLColonInFlowContext "
|
||||
"for details.", reader_.mark);
|
||||
throw new Error("While scanning a plain scalar", startMark,
|
||||
"found unexpected ':' . Please check "
|
||||
"http://pyyaml.org/wiki/YAMLColonInFlowContext "
|
||||
"for details.", reader_.mark);
|
||||
}
|
||||
|
||||
if(length == 0){break;}
|
||||
|
@ -1494,9 +1492,8 @@ final class Scanner
|
|||
{
|
||||
dchar c = reader_.peek();
|
||||
enforce(c == '!',
|
||||
new ScannerException("While scanning a " ~ name, startMark,
|
||||
"expected a '!', but found: " ~ to!string(c),
|
||||
reader_.mark));
|
||||
new Error("While scanning a " ~ name, startMark,
|
||||
"expected a '!', but found: " ~ to!string(c), reader_.mark));
|
||||
|
||||
uint length = 1;
|
||||
c = reader_.peek(length);
|
||||
|
@ -1510,9 +1507,9 @@ final class Scanner
|
|||
if(c != '!')
|
||||
{
|
||||
reader_.forward(length);
|
||||
throw new ScannerException("While scanning a " ~ name, startMark,
|
||||
"expected a '!', but found: " ~ to!string(c),
|
||||
reader_.mark);
|
||||
throw new Error("While scanning a " ~ name, startMark,
|
||||
"expected a '!', but found: " ~ to!string(c),
|
||||
reader_.mark);
|
||||
}
|
||||
++length;
|
||||
}
|
||||
|
@ -1544,9 +1541,8 @@ final class Scanner
|
|||
length = 0;
|
||||
}
|
||||
enforce(appender.data.length > 0,
|
||||
new ScannerException("While parsing a " ~ name, startMark,
|
||||
"expected URI, but found: " ~ to!string(c),
|
||||
reader_.mark));
|
||||
new Error("While parsing a " ~ name, startMark,
|
||||
"expected URI, but found: " ~ to!string(c), reader_.mark));
|
||||
|
||||
return appender.data;
|
||||
}
|
||||
|
@ -1567,11 +1563,11 @@ final class Scanner
|
|||
foreach(k; 0 .. 2)
|
||||
{
|
||||
dchar c = reader_.peek(k);
|
||||
enforce("0123456789ABCDEFabcdef".canFind(c),
|
||||
new ScannerException("While scanning a " ~ name, startMark,
|
||||
"expected URI escape sequence of "
|
||||
"2 hexadecimal numbers, but found: " ~
|
||||
to!string(c), reader_.mark));
|
||||
enforce(isHexDigit(c),
|
||||
new Error("While scanning a " ~ name, startMark,
|
||||
"expected URI escape sequence of "
|
||||
"2 hexadecimal numbers, but found: " ~
|
||||
to!string(c), reader_.mark));
|
||||
|
||||
uint digit;
|
||||
if(c - '0' < 10){digit = c - '0';}
|
||||
|
@ -1589,11 +1585,11 @@ final class Scanner
|
|||
try{return to!dstring(cast(string)bytes);}
|
||||
catch(ConvException e)
|
||||
{
|
||||
throw new ScannerException("While scanning a " ~ name, startMark, e.msg, mark);
|
||||
throw new Error("While scanning a " ~ name, startMark, e.msg, mark);
|
||||
}
|
||||
catch(UtfException e)
|
||||
{
|
||||
throw new ScannerException("While scanning a " ~ name, startMark, e.msg, mark);
|
||||
throw new Error("While scanning a " ~ name, startMark, e.msg, mark);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -11,6 +11,8 @@
|
|||
module dyaml.token;
|
||||
|
||||
|
||||
import std.conv;
|
||||
|
||||
import dyaml.encoding;
|
||||
import dyaml.exception;
|
||||
import dyaml.reader;
|
||||
|
@ -81,6 +83,9 @@ immutable struct Token
|
|||
ScalarStyle style;
|
||||
///Encoding, if this is a stream start token.
|
||||
Encoding encoding;
|
||||
|
||||
///Get string representation of the token ID.
|
||||
@property string idString() const {return to!string(id);}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
Loading…
Reference in a new issue