1 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file.
11 from cpp_namespace_environment
import CppNamespaceEnvironment
12 from model
import Model
, UnixName
14 def GenerateFilenames(full_namespace
):
15 # Try to find the file defining the namespace. Eg. for
16 # nameSpace.sub_name_space.Type' the following heuristics looks for:
17 # 1. name_space_sub_name_space.json,
18 # 2. name_space_sub_name_space.idl,
19 # 3. sub_name_space.json,
20 # 4. sub_name_space.idl,
22 sub_namespaces
= full_namespace
.split('.')
25 for namespace
in reversed(sub_namespaces
):
26 if basename
is not None:
27 basename
= UnixName(namespace
+ '.' + basename
)
29 basename
= UnixName(namespace
)
30 for ext
in ['json', 'idl']:
31 filenames
.append('%s.%s' % (basename
, ext
))
34 class SchemaLoader(object):
35 '''Resolves a type name into the namespace the type belongs to.
38 - |root| path to the root directory.
39 - |path| path to the directory with the API header files, relative to the
41 - |include_rules| List containing tuples with (path, cpp_namespace_pattern)
42 used when searching for types.
43 - |cpp_namespace_pattern| Default namespace pattern
49 cpp_namespace_pattern
):
51 self
._include
_rules
= [(path
, cpp_namespace_pattern
)]
52 self
._include
_rules
.extend(include_rules
)
54 def ResolveNamespace(self
, full_namespace
):
55 filenames
= GenerateFilenames(full_namespace
)
56 for path
, cpp_namespace
in self
._include
_rules
:
57 cpp_namespace_environment
= None
59 cpp_namespace_environment
= CppNamespaceEnvironment(cpp_namespace
)
60 for filename
in reversed(filenames
):
61 filepath
= os
.path
.join(path
, filename
);
62 if os
.path
.exists(os
.path
.join(self
._root
, filepath
)):
63 return Model().AddNamespace(
64 self
.LoadSchema(filepath
)[0],
66 environment
=cpp_namespace_environment
)
69 def ResolveType(self
, full_name
, default_namespace
):
70 name_parts
= full_name
.rsplit('.', 1)
71 if len(name_parts
) == 1:
72 if full_name
not in default_namespace
.types
:
74 return default_namespace
75 full_namespace
, type_name
= full_name
.rsplit('.', 1)
76 namespace
= self
.ResolveNamespace(full_namespace
)
77 if namespace
and type_name
in namespace
.types
:
81 def LoadSchema(self
, schema
):
82 '''Load a schema definition. The schema parameter must be a file name
83 with the full path relative to the root.'''
84 _
, schema_extension
= os
.path
.splitext(schema
)
86 schema_path
= os
.path
.join(self
._root
, schema
)
87 if schema_extension
== '.json':
88 api_defs
= json_schema
.Load(schema_path
)
89 elif schema_extension
== '.idl':
90 api_defs
= idl_schema
.Load(schema_path
)
92 sys
.exit('Did not recognize file extension %s for schema %s' %
93 (schema_extension
, schema
))