Skip to content

Commit 02403ff

Browse files
committed
Block reserved names in non-Introspection schemas
1 parent bbb959a commit 02403ff

File tree

2 files changed

+96
-22
lines changed

2 files changed

+96
-22
lines changed

include/SchemaLoader.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -276,6 +276,8 @@ class SchemaLoader
276276
void visitObjectTypeExtension(const peg::ast_node& objectTypeExtension);
277277
void visitDirectiveDefinition(const peg::ast_node& directiveDefinition);
278278

279+
static void blockReservedName(
280+
std::string_view name, std::optional<tao::graphqlpeg::position> position = std::nullopt);
279281
static OutputFieldList getOutputFields(const peg::ast_node::children_t& fields);
280282
static InputFieldList getInputFields(const peg::ast_node::children_t& fields);
281283

src/SchemaLoader.cpp

Lines changed: 94 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -649,8 +649,12 @@ void SchemaLoader::visitObjectTypeDefinition(const peg::ast_node& objectTypeDefi
649649
std::string_view description;
650650

651651
peg::on_first_child<peg::object_name>(objectTypeDefinition,
652-
[&name](const peg::ast_node& child) {
652+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
653653
name = child.string_view();
654+
if (!isIntrospection)
655+
{
656+
blockReservedName(name, child.begin());
657+
}
654658
});
655659

656660
peg::on_first_child<peg::description>(objectTypeDefinition,
@@ -676,9 +680,14 @@ void SchemaLoader::visitObjectTypeExtension(const peg::ast_node& objectTypeExten
676680
{
677681
std::string_view name;
678682

679-
peg::on_first_child<peg::object_name>(objectTypeExtension, [&name](const peg::ast_node& child) {
680-
name = child.string_view();
681-
});
683+
peg::on_first_child<peg::object_name>(objectTypeExtension,
684+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
685+
name = child.string_view();
686+
if (!isIntrospection)
687+
{
688+
blockReservedName(name, child.begin());
689+
}
690+
});
682691

683692
const auto itrType = _objectNames.find(name);
684693

@@ -710,8 +719,12 @@ void SchemaLoader::visitInterfaceTypeDefinition(const peg::ast_node& interfaceTy
710719
std::string_view description;
711720

712721
peg::on_first_child<peg::interface_name>(interfaceTypeDefinition,
713-
[&name](const peg::ast_node& child) {
722+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
714723
name = child.string_view();
724+
if (!isIntrospection)
725+
{
726+
blockReservedName(name, child.begin());
727+
}
715728
});
716729

717730
peg::on_first_child<peg::description>(interfaceTypeDefinition,
@@ -738,8 +751,12 @@ void SchemaLoader::visitInterfaceTypeExtension(const peg::ast_node& interfaceTyp
738751
std::string_view name;
739752

740753
peg::on_first_child<peg::interface_name>(interfaceTypeExtension,
741-
[&name](const peg::ast_node& child) {
754+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
742755
name = child.string_view();
756+
if (!isIntrospection)
757+
{
758+
blockReservedName(name, child.begin());
759+
}
743760
});
744761

745762
const auto itrType = _interfaceNames.find(name);
@@ -767,8 +784,12 @@ void SchemaLoader::visitInputObjectTypeDefinition(const peg::ast_node& inputObje
767784
std::string_view description;
768785

769786
peg::on_first_child<peg::object_name>(inputObjectTypeDefinition,
770-
[&name](const peg::ast_node& child) {
787+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
771788
name = child.string_view();
789+
if (!isIntrospection)
790+
{
791+
blockReservedName(name, child.begin());
792+
}
772793
});
773794

774795
peg::on_first_child<peg::description>(inputObjectTypeDefinition,
@@ -795,8 +816,12 @@ void SchemaLoader::visitInputObjectTypeExtension(const peg::ast_node& inputObjec
795816
std::string_view name;
796817

797818
peg::on_first_child<peg::object_name>(inputObjectTypeExtension,
798-
[&name](const peg::ast_node& child) {
819+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
799820
name = child.string_view();
821+
if (!isIntrospection)
822+
{
823+
blockReservedName(name, child.begin());
824+
}
800825
});
801826

802827
const auto itrType = _inputNames.find(name);
@@ -823,9 +848,14 @@ void SchemaLoader::visitEnumTypeDefinition(const peg::ast_node& enumTypeDefiniti
823848
std::string_view name;
824849
std::string_view description;
825850

826-
peg::on_first_child<peg::enum_name>(enumTypeDefinition, [&name](const peg::ast_node& child) {
827-
name = child.string_view();
828-
});
851+
peg::on_first_child<peg::enum_name>(enumTypeDefinition,
852+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
853+
name = child.string_view();
854+
if (!isIntrospection)
855+
{
856+
blockReservedName(name, child.begin());
857+
}
858+
});
829859

830860
peg::on_first_child<peg::description>(enumTypeDefinition,
831861
[&description](const peg::ast_node& child) {
@@ -850,9 +880,14 @@ void SchemaLoader::visitEnumTypeExtension(const peg::ast_node& enumTypeExtension
850880
{
851881
std::string_view name;
852882

853-
peg::on_first_child<peg::enum_name>(enumTypeExtension, [&name](const peg::ast_node& child) {
854-
name = child.string_view();
855-
});
883+
peg::on_first_child<peg::enum_name>(enumTypeExtension,
884+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
885+
name = child.string_view();
886+
if (!isIntrospection)
887+
{
888+
blockReservedName(name, child.begin());
889+
}
890+
});
856891

857892
const auto itrType = _enumNames.find(name);
858893

@@ -928,8 +963,12 @@ void SchemaLoader::visitScalarTypeDefinition(const peg::ast_node& scalarTypeDefi
928963
std::string_view description;
929964

930965
peg::on_first_child<peg::scalar_name>(scalarTypeDefinition,
931-
[&name](const peg::ast_node& child) {
966+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
932967
name = child.string_view();
968+
if (!isIntrospection)
969+
{
970+
blockReservedName(name, child.begin());
971+
}
933972
});
934973

935974
peg::on_first_child<peg::description>(scalarTypeDefinition,
@@ -951,9 +990,14 @@ void SchemaLoader::visitUnionTypeDefinition(const peg::ast_node& unionTypeDefini
951990
std::string_view name;
952991
std::string_view description;
953992

954-
peg::on_first_child<peg::union_name>(unionTypeDefinition, [&name](const peg::ast_node& child) {
955-
name = child.string_view();
956-
});
993+
peg::on_first_child<peg::union_name>(unionTypeDefinition,
994+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
995+
name = child.string_view();
996+
if (!isIntrospection)
997+
{
998+
blockReservedName(name, child.begin());
999+
}
1000+
});
9571001

9581002
peg::on_first_child<peg::description>(unionTypeDefinition,
9591003
[&description](const peg::ast_node& child) {
@@ -978,9 +1022,14 @@ void SchemaLoader::visitUnionTypeExtension(const peg::ast_node& unionTypeExtensi
9781022
{
9791023
std::string_view name;
9801024

981-
peg::on_first_child<peg::union_name>(unionTypeExtension, [&name](const peg::ast_node& child) {
982-
name = child.string_view();
983-
});
1025+
peg::on_first_child<peg::union_name>(unionTypeExtension,
1026+
[isIntrospection = _isIntrospection, &name](const peg::ast_node& child) {
1027+
name = child.string_view();
1028+
if (!isIntrospection)
1029+
{
1030+
blockReservedName(name, child.begin());
1031+
}
1032+
});
9841033

9851034
const auto itrType = _unionNames.find(name);
9861035

@@ -1000,8 +1049,12 @@ void SchemaLoader::visitDirectiveDefinition(const peg::ast_node& directiveDefini
10001049
Directive directive;
10011050

10021051
peg::on_first_child<peg::directive_name>(directiveDefinition,
1003-
[&directive](const peg::ast_node& child) {
1052+
[isIntrospection = _isIntrospection, &directive](const peg::ast_node& child) {
10041053
directive.name = child.string_view();
1054+
if (!isIntrospection)
1055+
{
1056+
blockReservedName(directive.name, child.begin());
1057+
}
10051058
});
10061059

10071060
peg::on_first_child<peg::description>(directiveDefinition,
@@ -1067,6 +1120,25 @@ std::string_view SchemaLoader::getSafeCppName(std::string_view type) noexcept
10671120
return (safeNames.cend() == itr) ? type : itr->second->second;
10681121
}
10691122

1123+
void SchemaLoader::blockReservedName(
1124+
std::string_view name, std::optional<tao::graphqlpeg::position> position)
1125+
{
1126+
// https://spec.graphql.org/June2018/#sec-Reserved-Names
1127+
if (name.size() > 1 && name.substr(0, 2) == R"gql(__)gql"sv)
1128+
{
1129+
std::ostringstream error;
1130+
1131+
error << "Names starting with __ are reserved: " << name;
1132+
1133+
if (position)
1134+
{
1135+
error << " line: " << position->line << " column: " << position->column;
1136+
}
1137+
1138+
throw std::runtime_error(error.str());
1139+
}
1140+
}
1141+
10701142
OutputFieldList SchemaLoader::getOutputFields(const peg::ast_node::children_t& fields)
10711143
{
10721144
OutputFieldList outputFields;

0 commit comments

Comments
 (0)