We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
conan search <reference> for recipe without binary packages
In case there is a recipe without binary packages in the local cache, `conan search` with a full reference just prints 
`There are no packages for pattern '<ref>'`
- "pattern" is wrong, should be "reference"
- Something like "Package recipe found" would be nice.
- The same command with a suffixed "*" gives more information, although the request is less specific.

This happens mainly when `conan create` fails between export and package. I was confused about the inconsistent outputs with pattern and reference.

Steps to reproduce:
```
> conan search zlib*
There are no packages matching the zlib* pattern

> conan info zlib/1.2.11@conan/stable
...downloads the recipe

> conan search zlib*
Existing package recipes:
zlib/1.2.11@conan/stable

> conan search zlib/1.2.11@conan/stable*
Existing package recipes:
zlib/1.2.11@conan/stable

> conan search zlib/1.2.11@conan/stable
There are no packages for pattern 'zlib/1.2.11@conan/stable'
```

Conan 1.0.1, Windows 
- [x] I've read the [CONTRIBUTING guide](https://raw.githubusercontent.com/conan-io/conan/develop/.github/CONTRIBUTING.md).
- [x] I've specified the Conan version, operating system version and any tool that can be relevant.
- [x] I've explained the steps to reproduce the error or the motivation/use case of the question/suggestion.



--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `conans/client/printer.py`
Content:
```
1 from collections import OrderedDict
2 
3 from conans.paths import SimplePaths
4 
5 from conans.client.output import Color
6 from conans.model.ref import ConanFileReference
7 from conans.model.ref import PackageReference
8 from conans.client.installer import build_id
9 import fnmatch
10 
11 
12 class Printer(object):
13     """ Print some specific information """
14 
15     INDENT_COLOR = {0: Color.BRIGHT_CYAN,
16                     1: Color.BRIGHT_RED,
17                     2: Color.BRIGHT_GREEN,
18                     3: Color.BRIGHT_YELLOW,
19                     4: Color.BRIGHT_MAGENTA}
20 
21     INDENT_SPACES = 4
22 
23     def __init__(self, out):
24         self._out = out
25 
26     def print_graph(self, deps_graph, registry):
27         """ Simple pretty printing of a deps graph, can be improved
28         with options, info like licenses, etc
29         """
30         self._out.writeln("Requirements", Color.BRIGHT_YELLOW)
31         for node in sorted(deps_graph.nodes):
32             ref, _ = node
33             if not ref:
34                 continue
35             remote = registry.get_ref(ref)
36             from_text = "from local cache" if not remote else "from '%s'" % remote.name
37             self._out.writeln("    %s %s" % (repr(ref), from_text), Color.BRIGHT_CYAN)
38         self._out.writeln("Packages", Color.BRIGHT_YELLOW)
39         for node in sorted(deps_graph.nodes):
40             ref, conanfile = node
41             if not ref:
42                 continue
43             ref = PackageReference(ref, conanfile.info.package_id())
44             self._out.writeln("    %s" % repr(ref), Color.BRIGHT_CYAN)
45         self._out.writeln("")
46 
47     def _print_paths(self, ref, conan, path_resolver, show):
48         if isinstance(ref, ConanFileReference):
49             if show("export_folder"):
50                 path = path_resolver.export(ref)
51                 self._out.writeln("    export_folder: %s" % path, Color.BRIGHT_GREEN)
52             if show("source_folder"):
53                 path = path_resolver.source(ref, conan.short_paths)
54                 self._out.writeln("    source_folder: %s" % path, Color.BRIGHT_GREEN)
55             if show("build_folder") and isinstance(path_resolver, SimplePaths):
56                 # @todo: check if this is correct or if it must always be package_id()
57                 bid = build_id(conan)
58                 if not bid:
59                     bid = conan.info.package_id()
60                 path = path_resolver.build(PackageReference(ref, bid), conan.short_paths)
61                 self._out.writeln("    build_folder: %s" % path, Color.BRIGHT_GREEN)
62             if show("package_folder") and isinstance(path_resolver, SimplePaths):
63                 id_ = conan.info.package_id()
64                 path = path_resolver.package(PackageReference(ref, id_), conan.short_paths)
65                 self._out.writeln("    package_folder: %s" % path, Color.BRIGHT_GREEN)
66 
67     def print_info(self, deps_graph, project_reference, _info, registry, graph_updates_info=None,
68                    remote=None, node_times=None, path_resolver=None, package_filter=None,
69                    show_paths=False):
70         """ Print the dependency information for a conan file
71 
72             Attributes:
73                 deps_graph: the dependency graph of conan file references to print
74                 placeholder_reference: the conan file reference that represents the conan
75                                        file for a project on the path. This may be None,
76                                        in which case the project itself will not be part
77                                        of the printed dependencies.
78                 remote: Remote specified in install command.
79                         Could be different from the registry one.
80         """
81         if _info is None:  # No filter
82             def show(_):
83                 return True
84         else:
85             _info_lower = [s.lower() for s in _info]
86 
87             def show(field):
88                 return field in _info_lower
89 
90         graph_updates_info = graph_updates_info or {}
91         for node in sorted(deps_graph.nodes):
92             ref, conan = node
93             if not ref:
94                 # ref is only None iff info is being printed for a project directory, and
95                 # not a passed in reference
96                 if project_reference is None:
97                     continue
98                 else:
99                     ref = project_reference
100             if package_filter and not fnmatch.fnmatch(str(ref), package_filter):
101                 continue
102 
103             self._out.writeln("%s" % str(ref), Color.BRIGHT_CYAN)
104             reg_remote = registry.get_ref(ref)
105             # Excludes PROJECT fake reference
106             remote_name = remote
107             if reg_remote and not remote:
108                 remote_name = reg_remote.name
109 
110             if show("id"):
111                 id_ = conan.info.package_id()
112                 self._out.writeln("    ID: %s" % id_, Color.BRIGHT_GREEN)
113             if show("build_id"):
114                 bid = build_id(conan)
115                 self._out.writeln("    BuildID: %s" % bid, Color.BRIGHT_GREEN)
116 
117             if show_paths:
118                 self._print_paths(ref, conan, path_resolver, show)
119 
120             if isinstance(ref, ConanFileReference) and show("remote"):
121                 if reg_remote:
122                     self._out.writeln("    Remote: %s=%s" % (reg_remote.name, reg_remote.url),
123                                       Color.BRIGHT_GREEN)
124                 else:
125                     self._out.writeln("    Remote: None", Color.BRIGHT_GREEN)
126             url = getattr(conan, "url", None)
127             license_ = getattr(conan, "license", None)
128             author = getattr(conan, "author", None)
129             if url and show("url"):
130                 self._out.writeln("    URL: %s" % url, Color.BRIGHT_GREEN)
131 
132             if license_ and show("license"):
133                 if isinstance(license_, (list, tuple, set)):
134                     self._out.writeln("    Licenses: %s" % ", ".join(license_), Color.BRIGHT_GREEN)
135                 else:
136                     self._out.writeln("    License: %s" % license_, Color.BRIGHT_GREEN)
137             if author and show("author"):
138                 self._out.writeln("    Author: %s" % author, Color.BRIGHT_GREEN)
139 
140             if isinstance(ref, ConanFileReference) and show("update"):  # Excludes PROJECT
141                 update = graph_updates_info.get(ref)
142                 update_messages = {
143                  None: ("Version not checked", Color.WHITE),
144                  0: ("You have the latest version (%s)" % remote_name, Color.BRIGHT_GREEN),
145                  1: ("There is a newer version (%s)" % remote_name, Color.BRIGHT_YELLOW),
146                  -1: ("The local file is newer than remote's one (%s)" % remote_name,
147                       Color.BRIGHT_RED)
148                 }
149                 self._out.writeln("    Updates: %s" % update_messages[update][0],
150                                   update_messages[update][1])
151 
152             if node_times and node_times.get(ref, None) and show("date"):
153                 self._out.writeln("    Creation date: %s" % node_times.get(ref, None),
154                                   Color.BRIGHT_GREEN)
155 
156             dependants = deps_graph.inverse_neighbors(node)
157             if isinstance(ref, ConanFileReference) and show("required"):  # Excludes
158                 self._out.writeln("    Required by:", Color.BRIGHT_GREEN)
159                 for d in dependants:
160                     ref = d.conan_ref if d.conan_ref else project_reference
161                     self._out.writeln("        %s" % str(ref), Color.BRIGHT_YELLOW)
162 
163             if show("requires"):
164                 depends = deps_graph.neighbors(node)
165                 if depends:
166                     self._out.writeln("    Requires:", Color.BRIGHT_GREEN)
167                     for d in depends:
168                         self._out.writeln("        %s" % repr(d.conan_ref), Color.BRIGHT_YELLOW)
169 
170     def print_search_recipes(self, references, pattern, raw):
171         """ Print all the exported conans information
172         param pattern: wildcards, e.g., "opencv/*"
173         """
174         if not references and not raw:
175             warn_msg = "There are no packages"
176             pattern_msg = " matching the '%s' pattern" % pattern
177             self._out.info(warn_msg + pattern_msg if pattern else warn_msg)
178             return
179 
180         if not raw:
181             self._out.info("Existing package recipes:\n")
182             if isinstance(references, dict):
183                 for remote, refs in references.items():
184                     self._out.highlight("Remote '%s':" % str(remote))
185                     for conan_ref in sorted(refs):
186                         self._print_colored_line(str(conan_ref), indent=0)
187             else:
188                 for conan_ref in sorted(references):
189                     self._print_colored_line(str(conan_ref), indent=0)
190         else:
191             if isinstance(references, dict):
192                 for remote, refs in references.items():
193                     self._out.writeln("Remote '%s':" % str(remote))
194                     for conan_ref in sorted(refs):
195                         self._out.writeln(str(conan_ref))
196             else:
197                 self._out.writeln("\n".join([str(ref) for ref in references]))
198 
199     def print_search_packages(self, packages_props, reference, recipe_hash, packages_query):
200         if not packages_props:
201             if packages_query:
202                 warn_msg = "There are no packages for reference '%s' matching the query '%s'" % (str(reference),
203                                                                                                  packages_query)
204             else:
205                 warn_msg = "There are no packages for pattern '%s'" % str(reference)
206             self._out.info(warn_msg)
207             return
208 
209         self._out.info("Existing packages for recipe %s:\n" % str(reference))
210         # Each package
211         for package_id, properties in sorted(packages_props.items()):
212             self._print_colored_line("Package_ID", package_id, 1)
213             for section in ("options", "settings", "full_requires"):
214                 attrs = properties.get(section, [])
215                 if attrs:
216                     section_name = {"full_requires": "requires"}.get(section, section)
217                     self._print_colored_line("[%s]" % section_name, indent=2)
218                     if isinstance(attrs, dict):  # options, settings
219                         attrs = OrderedDict(sorted(attrs.items()))
220                         for key, value in attrs.items():
221                             self._print_colored_line(key, value=value, indent=3)
222                     elif isinstance(attrs, list):  # full requires
223                         for key in sorted(attrs):
224                             self._print_colored_line(key, indent=3)
225             package_recipe_hash = properties.get("recipe_hash", None)
226             # Always compare outdated with local recipe, simplification,
227             # if a remote check is needed install recipe first
228             if recipe_hash:
229                 self._print_colored_line("Outdated from recipe: %s" % (recipe_hash != package_recipe_hash), indent=2)
230             self._out.writeln("")
231 
232     def print_profile(self, name, profile):
233         self._out.info("Configuration for profile %s:\n" % name)
234         self._print_profile_section("settings", profile.settings.items(), separator="=")
235         self._print_profile_section("options", profile.options.as_list(), separator="=")
236         self._print_profile_section("build_requires", [(key, ", ".join(str(val) for val in values))
237                                                        for key, values in
238                                                        profile.build_requires.items()])
239 
240         envs = []
241         for package, env_vars in profile.env_values.data.items():
242             for name, value in env_vars.items():
243                 key = "%s:%s" % (package, name) if package else name
244                 envs.append((key, value))
245         self._print_profile_section("env", envs, separator='=')
246 
247     def _print_profile_section(self, name, items, indent=0, separator=": "):
248         self._print_colored_line("[%s]" % name, indent=indent, color=Color.BRIGHT_RED)
249         for key, value in items:
250             self._print_colored_line(key, value=str(value), indent=0, separator=separator)
251 
252     def _print_colored_line(self, text, value=None, indent=0, separator=": ", color=None):
253         """ Print a colored line depending on its indentation level
254             Attributes:
255                 text: string line
256                 split_symbol: if you want an output with different in-line colors
257                 indent_plus: integer to add a plus indentation
258         """
259         text = text.strip()
260         if not text:
261             return
262 
263         text_color = Printer.INDENT_COLOR.get(indent, Color.BRIGHT_WHITE) if not color else color
264         indent_text = ' ' * Printer.INDENT_SPACES * indent
265         if value is not None:
266             value_color = Color.BRIGHT_WHITE
267             self._out.write('%s%s%s' % (indent_text, text, separator), text_color)
268             self._out.writeln(value, value_color)
269         else:
270             self._out.writeln('%s%s' % (indent_text, text), text_color)
271
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/conans/client/printer.py b/conans/client/printer.py
--- a/conans/client/printer.py
+++ b/conans/client/printer.py
@@ -202,7 +202,11 @@
                 warn_msg = "There are no packages for reference '%s' matching the query '%s'" % (str(reference),
                                                                                                  packages_query)
             else:
-                warn_msg = "There are no packages for pattern '%s'" % str(reference)
+                warn_msg = "There are no packages for reference '%s'" % str(reference)
+
+            if recipe_hash:
+                warn_msg += ", but package recipe found."
+
             self._out.info(warn_msg)
             return

{"golden_diff": "diff --git a/conans/client/printer.py b/conans/client/printer.py\n--- a/conans/client/printer.py\n+++ b/conans/client/printer.py\n@@ -202,7 +202,11 @@\n                 warn_msg = \"There are no packages for reference '%s' matching the query '%s'\" % (str(reference),\n                                                                                                  packages_query)\n             else:\n-                warn_msg = \"There are no packages for pattern '%s'\" % str(reference)\n+                warn_msg = \"There are no packages for reference '%s'\" % str(reference)\n+\n+            if recipe_hash:\n+                warn_msg += \", but package recipe found.\"\n+\n             self._out.info(warn_msg)\n             return\n", "issue": "conan search <reference> for recipe without binary packages\nIn case there is a recipe without binary packages in the local cache, `conan search` with a full reference just prints \r\n`There are no packages for pattern '<ref>'`\r\n- \"pattern\" is wrong, should be \"reference\"\r\n- Something like \"Package recipe found\" would be nice.\r\n- The same command with a suffixed \"*\" gives more information, although the request is less specific.\r\n\r\nThis happens mainly when `conan create` fails between export and package. I was confused about the inconsistent outputs with pattern and reference.\r\n\r\nSteps to reproduce:\r\n```\r\n> conan search zlib*\r\nThere are no packages matching the zlib* pattern\r\n\r\n> conan info zlib/1.2.11@conan/stable\r\n...downloads the recipe\r\n\r\n> conan search zlib*\r\nExisting package recipes:\r\nzlib/1.2.11@conan/stable\r\n\r\n> conan search zlib/1.2.11@conan/stable*\r\nExisting package recipes:\r\nzlib/1.2.11@conan/stable\r\n\r\n> conan search zlib/1.2.11@conan/stable\r\nThere are no packages for pattern 'zlib/1.2.11@conan/stable'\r\n```\r\n\r\nConan 1.0.1, Windows \r\n- [x] I've read the [CONTRIBUTING guide](https://raw.githubusercontent.com/conan-io/conan/develop/.github/CONTRIBUTING.md).\r\n- [x] I've specified the Conan version, operating system version and any tool that can be relevant.\r\n- [x] I've explained the steps to reproduce the error or the motivation/use case of the question/suggestion.\r\n\r\n\n", "before_files": [{"content": "from collections import OrderedDict\n\nfrom conans.paths import SimplePaths\n\nfrom conans.client.output import Color\nfrom conans.model.ref import ConanFileReference\nfrom conans.model.ref import PackageReference\nfrom conans.client.installer import build_id\nimport fnmatch\n\n\nclass Printer(object):\n    \"\"\" Print some specific information \"\"\"\n\n    INDENT_COLOR = {0: Color.BRIGHT_CYAN,\n                    1: Color.BRIGHT_RED,\n                    2: Color.BRIGHT_GREEN,\n                    3: Color.BRIGHT_YELLOW,\n                    4: Color.BRIGHT_MAGENTA}\n\n    INDENT_SPACES = 4\n\n    def __init__(self, out):\n        self._out = out\n\n    def print_graph(self, deps_graph, registry):\n        \"\"\" Simple pretty printing of a deps graph, can be improved\n        with options, info like licenses, etc\n        \"\"\"\n        self._out.writeln(\"Requirements\", Color.BRIGHT_YELLOW)\n        for node in sorted(deps_graph.nodes):\n            ref, _ = node\n            if not ref:\n                continue\n            remote = registry.get_ref(ref)\n            from_text = \"from local cache\" if not remote else \"from '%s'\" % remote.name\n            self._out.writeln(\"    %s %s\" % (repr(ref), from_text), Color.BRIGHT_CYAN)\n        self._out.writeln(\"Packages\", Color.BRIGHT_YELLOW)\n        for node in sorted(deps_graph.nodes):\n            ref, conanfile = node\n            if not ref:\n                continue\n            ref = PackageReference(ref, conanfile.info.package_id())\n            self._out.writeln(\"    %s\" % repr(ref), Color.BRIGHT_CYAN)\n        self._out.writeln(\"\")\n\n    def _print_paths(self, ref, conan, path_resolver, show):\n        if isinstance(ref, ConanFileReference):\n            if show(\"export_folder\"):\n                path = path_resolver.export(ref)\n                self._out.writeln(\"    export_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"source_folder\"):\n                path = path_resolver.source(ref, conan.short_paths)\n                self._out.writeln(\"    source_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"build_folder\") and isinstance(path_resolver, SimplePaths):\n                # @todo: check if this is correct or if it must always be package_id()\n                bid = build_id(conan)\n                if not bid:\n                    bid = conan.info.package_id()\n                path = path_resolver.build(PackageReference(ref, bid), conan.short_paths)\n                self._out.writeln(\"    build_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"package_folder\") and isinstance(path_resolver, SimplePaths):\n                id_ = conan.info.package_id()\n                path = path_resolver.package(PackageReference(ref, id_), conan.short_paths)\n                self._out.writeln(\"    package_folder: %s\" % path, Color.BRIGHT_GREEN)\n\n    def print_info(self, deps_graph, project_reference, _info, registry, graph_updates_info=None,\n                   remote=None, node_times=None, path_resolver=None, package_filter=None,\n                   show_paths=False):\n        \"\"\" Print the dependency information for a conan file\n\n            Attributes:\n                deps_graph: the dependency graph of conan file references to print\n                placeholder_reference: the conan file reference that represents the conan\n                                       file for a project on the path. This may be None,\n                                       in which case the project itself will not be part\n                                       of the printed dependencies.\n                remote: Remote specified in install command.\n                        Could be different from the registry one.\n        \"\"\"\n        if _info is None:  # No filter\n            def show(_):\n                return True\n        else:\n            _info_lower = [s.lower() for s in _info]\n\n            def show(field):\n                return field in _info_lower\n\n        graph_updates_info = graph_updates_info or {}\n        for node in sorted(deps_graph.nodes):\n            ref, conan = node\n            if not ref:\n                # ref is only None iff info is being printed for a project directory, and\n                # not a passed in reference\n                if project_reference is None:\n                    continue\n                else:\n                    ref = project_reference\n            if package_filter and not fnmatch.fnmatch(str(ref), package_filter):\n                continue\n\n            self._out.writeln(\"%s\" % str(ref), Color.BRIGHT_CYAN)\n            reg_remote = registry.get_ref(ref)\n            # Excludes PROJECT fake reference\n            remote_name = remote\n            if reg_remote and not remote:\n                remote_name = reg_remote.name\n\n            if show(\"id\"):\n                id_ = conan.info.package_id()\n                self._out.writeln(\"    ID: %s\" % id_, Color.BRIGHT_GREEN)\n            if show(\"build_id\"):\n                bid = build_id(conan)\n                self._out.writeln(\"    BuildID: %s\" % bid, Color.BRIGHT_GREEN)\n\n            if show_paths:\n                self._print_paths(ref, conan, path_resolver, show)\n\n            if isinstance(ref, ConanFileReference) and show(\"remote\"):\n                if reg_remote:\n                    self._out.writeln(\"    Remote: %s=%s\" % (reg_remote.name, reg_remote.url),\n                                      Color.BRIGHT_GREEN)\n                else:\n                    self._out.writeln(\"    Remote: None\", Color.BRIGHT_GREEN)\n            url = getattr(conan, \"url\", None)\n            license_ = getattr(conan, \"license\", None)\n            author = getattr(conan, \"author\", None)\n            if url and show(\"url\"):\n                self._out.writeln(\"    URL: %s\" % url, Color.BRIGHT_GREEN)\n\n            if license_ and show(\"license\"):\n                if isinstance(license_, (list, tuple, set)):\n                    self._out.writeln(\"    Licenses: %s\" % \", \".join(license_), Color.BRIGHT_GREEN)\n                else:\n                    self._out.writeln(\"    License: %s\" % license_, Color.BRIGHT_GREEN)\n            if author and show(\"author\"):\n                self._out.writeln(\"    Author: %s\" % author, Color.BRIGHT_GREEN)\n\n            if isinstance(ref, ConanFileReference) and show(\"update\"):  # Excludes PROJECT\n                update = graph_updates_info.get(ref)\n                update_messages = {\n                 None: (\"Version not checked\", Color.WHITE),\n                 0: (\"You have the latest version (%s)\" % remote_name, Color.BRIGHT_GREEN),\n                 1: (\"There is a newer version (%s)\" % remote_name, Color.BRIGHT_YELLOW),\n                 -1: (\"The local file is newer than remote's one (%s)\" % remote_name,\n                      Color.BRIGHT_RED)\n                }\n                self._out.writeln(\"    Updates: %s\" % update_messages[update][0],\n                                  update_messages[update][1])\n\n            if node_times and node_times.get(ref, None) and show(\"date\"):\n                self._out.writeln(\"    Creation date: %s\" % node_times.get(ref, None),\n                                  Color.BRIGHT_GREEN)\n\n            dependants = deps_graph.inverse_neighbors(node)\n            if isinstance(ref, ConanFileReference) and show(\"required\"):  # Excludes\n                self._out.writeln(\"    Required by:\", Color.BRIGHT_GREEN)\n                for d in dependants:\n                    ref = d.conan_ref if d.conan_ref else project_reference\n                    self._out.writeln(\"        %s\" % str(ref), Color.BRIGHT_YELLOW)\n\n            if show(\"requires\"):\n                depends = deps_graph.neighbors(node)\n                if depends:\n                    self._out.writeln(\"    Requires:\", Color.BRIGHT_GREEN)\n                    for d in depends:\n                        self._out.writeln(\"        %s\" % repr(d.conan_ref), Color.BRIGHT_YELLOW)\n\n    def print_search_recipes(self, references, pattern, raw):\n        \"\"\" Print all the exported conans information\n        param pattern: wildcards, e.g., \"opencv/*\"\n        \"\"\"\n        if not references and not raw:\n            warn_msg = \"There are no packages\"\n            pattern_msg = \" matching the '%s' pattern\" % pattern\n            self._out.info(warn_msg + pattern_msg if pattern else warn_msg)\n            return\n\n        if not raw:\n            self._out.info(\"Existing package recipes:\\n\")\n            if isinstance(references, dict):\n                for remote, refs in references.items():\n                    self._out.highlight(\"Remote '%s':\" % str(remote))\n                    for conan_ref in sorted(refs):\n                        self._print_colored_line(str(conan_ref), indent=0)\n            else:\n                for conan_ref in sorted(references):\n                    self._print_colored_line(str(conan_ref), indent=0)\n        else:\n            if isinstance(references, dict):\n                for remote, refs in references.items():\n                    self._out.writeln(\"Remote '%s':\" % str(remote))\n                    for conan_ref in sorted(refs):\n                        self._out.writeln(str(conan_ref))\n            else:\n                self._out.writeln(\"\\n\".join([str(ref) for ref in references]))\n\n    def print_search_packages(self, packages_props, reference, recipe_hash, packages_query):\n        if not packages_props:\n            if packages_query:\n                warn_msg = \"There are no packages for reference '%s' matching the query '%s'\" % (str(reference),\n                                                                                                 packages_query)\n            else:\n                warn_msg = \"There are no packages for pattern '%s'\" % str(reference)\n            self._out.info(warn_msg)\n            return\n\n        self._out.info(\"Existing packages for recipe %s:\\n\" % str(reference))\n        # Each package\n        for package_id, properties in sorted(packages_props.items()):\n            self._print_colored_line(\"Package_ID\", package_id, 1)\n            for section in (\"options\", \"settings\", \"full_requires\"):\n                attrs = properties.get(section, [])\n                if attrs:\n                    section_name = {\"full_requires\": \"requires\"}.get(section, section)\n                    self._print_colored_line(\"[%s]\" % section_name, indent=2)\n                    if isinstance(attrs, dict):  # options, settings\n                        attrs = OrderedDict(sorted(attrs.items()))\n                        for key, value in attrs.items():\n                            self._print_colored_line(key, value=value, indent=3)\n                    elif isinstance(attrs, list):  # full requires\n                        for key in sorted(attrs):\n                            self._print_colored_line(key, indent=3)\n            package_recipe_hash = properties.get(\"recipe_hash\", None)\n            # Always compare outdated with local recipe, simplification,\n            # if a remote check is needed install recipe first\n            if recipe_hash:\n                self._print_colored_line(\"Outdated from recipe: %s\" % (recipe_hash != package_recipe_hash), indent=2)\n            self._out.writeln(\"\")\n\n    def print_profile(self, name, profile):\n        self._out.info(\"Configuration for profile %s:\\n\" % name)\n        self._print_profile_section(\"settings\", profile.settings.items(), separator=\"=\")\n        self._print_profile_section(\"options\", profile.options.as_list(), separator=\"=\")\n        self._print_profile_section(\"build_requires\", [(key, \", \".join(str(val) for val in values))\n                                                       for key, values in\n                                                       profile.build_requires.items()])\n\n        envs = []\n        for package, env_vars in profile.env_values.data.items():\n            for name, value in env_vars.items():\n                key = \"%s:%s\" % (package, name) if package else name\n                envs.append((key, value))\n        self._print_profile_section(\"env\", envs, separator='=')\n\n    def _print_profile_section(self, name, items, indent=0, separator=\": \"):\n        self._print_colored_line(\"[%s]\" % name, indent=indent, color=Color.BRIGHT_RED)\n        for key, value in items:\n            self._print_colored_line(key, value=str(value), indent=0, separator=separator)\n\n    def _print_colored_line(self, text, value=None, indent=0, separator=\": \", color=None):\n        \"\"\" Print a colored line depending on its indentation level\n            Attributes:\n                text: string line\n                split_symbol: if you want an output with different in-line colors\n                indent_plus: integer to add a plus indentation\n        \"\"\"\n        text = text.strip()\n        if not text:\n            return\n\n        text_color = Printer.INDENT_COLOR.get(indent, Color.BRIGHT_WHITE) if not color else color\n        indent_text = ' ' * Printer.INDENT_SPACES * indent\n        if value is not None:\n            value_color = Color.BRIGHT_WHITE\n            self._out.write('%s%s%s' % (indent_text, text, separator), text_color)\n            self._out.writeln(value, value_color)\n        else:\n            self._out.writeln('%s%s' % (indent_text, text), text_color)\n", "path": "conans/client/printer.py"}], "after_files": [{"content": "from collections import OrderedDict\n\nfrom conans.paths import SimplePaths\n\nfrom conans.client.output import Color\nfrom conans.model.ref import ConanFileReference\nfrom conans.model.ref import PackageReference\nfrom conans.client.installer import build_id\nimport fnmatch\n\n\nclass Printer(object):\n    \"\"\" Print some specific information \"\"\"\n\n    INDENT_COLOR = {0: Color.BRIGHT_CYAN,\n                    1: Color.BRIGHT_RED,\n                    2: Color.BRIGHT_GREEN,\n                    3: Color.BRIGHT_YELLOW,\n                    4: Color.BRIGHT_MAGENTA}\n\n    INDENT_SPACES = 4\n\n    def __init__(self, out):\n        self._out = out\n\n    def print_graph(self, deps_graph, registry):\n        \"\"\" Simple pretty printing of a deps graph, can be improved\n        with options, info like licenses, etc\n        \"\"\"\n        self._out.writeln(\"Requirements\", Color.BRIGHT_YELLOW)\n        for node in sorted(deps_graph.nodes):\n            ref, _ = node\n            if not ref:\n                continue\n            remote = registry.get_ref(ref)\n            from_text = \"from local cache\" if not remote else \"from '%s'\" % remote.name\n            self._out.writeln(\"    %s %s\" % (repr(ref), from_text), Color.BRIGHT_CYAN)\n        self._out.writeln(\"Packages\", Color.BRIGHT_YELLOW)\n        for node in sorted(deps_graph.nodes):\n            ref, conanfile = node\n            if not ref:\n                continue\n            ref = PackageReference(ref, conanfile.info.package_id())\n            self._out.writeln(\"    %s\" % repr(ref), Color.BRIGHT_CYAN)\n        self._out.writeln(\"\")\n\n    def _print_paths(self, ref, conan, path_resolver, show):\n        if isinstance(ref, ConanFileReference):\n            if show(\"export_folder\"):\n                path = path_resolver.export(ref)\n                self._out.writeln(\"    export_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"source_folder\"):\n                path = path_resolver.source(ref, conan.short_paths)\n                self._out.writeln(\"    source_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"build_folder\") and isinstance(path_resolver, SimplePaths):\n                # @todo: check if this is correct or if it must always be package_id()\n                bid = build_id(conan)\n                if not bid:\n                    bid = conan.info.package_id()\n                path = path_resolver.build(PackageReference(ref, bid), conan.short_paths)\n                self._out.writeln(\"    build_folder: %s\" % path, Color.BRIGHT_GREEN)\n            if show(\"package_folder\") and isinstance(path_resolver, SimplePaths):\n                id_ = conan.info.package_id()\n                path = path_resolver.package(PackageReference(ref, id_), conan.short_paths)\n                self._out.writeln(\"    package_folder: %s\" % path, Color.BRIGHT_GREEN)\n\n    def print_info(self, deps_graph, project_reference, _info, registry, graph_updates_info=None,\n                   remote=None, node_times=None, path_resolver=None, package_filter=None,\n                   show_paths=False):\n        \"\"\" Print the dependency information for a conan file\n\n            Attributes:\n                deps_graph: the dependency graph of conan file references to print\n                placeholder_reference: the conan file reference that represents the conan\n                                       file for a project on the path. This may be None,\n                                       in which case the project itself will not be part\n                                       of the printed dependencies.\n                remote: Remote specified in install command.\n                        Could be different from the registry one.\n        \"\"\"\n        if _info is None:  # No filter\n            def show(_):\n                return True\n        else:\n            _info_lower = [s.lower() for s in _info]\n\n            def show(field):\n                return field in _info_lower\n\n        graph_updates_info = graph_updates_info or {}\n        for node in sorted(deps_graph.nodes):\n            ref, conan = node\n            if not ref:\n                # ref is only None iff info is being printed for a project directory, and\n                # not a passed in reference\n                if project_reference is None:\n                    continue\n                else:\n                    ref = project_reference\n            if package_filter and not fnmatch.fnmatch(str(ref), package_filter):\n                continue\n\n            self._out.writeln(\"%s\" % str(ref), Color.BRIGHT_CYAN)\n            reg_remote = registry.get_ref(ref)\n            # Excludes PROJECT fake reference\n            remote_name = remote\n            if reg_remote and not remote:\n                remote_name = reg_remote.name\n\n            if show(\"id\"):\n                id_ = conan.info.package_id()\n                self._out.writeln(\"    ID: %s\" % id_, Color.BRIGHT_GREEN)\n            if show(\"build_id\"):\n                bid = build_id(conan)\n                self._out.writeln(\"    BuildID: %s\" % bid, Color.BRIGHT_GREEN)\n\n            if show_paths:\n                self._print_paths(ref, conan, path_resolver, show)\n\n            if isinstance(ref, ConanFileReference) and show(\"remote\"):\n                if reg_remote:\n                    self._out.writeln(\"    Remote: %s=%s\" % (reg_remote.name, reg_remote.url),\n                                      Color.BRIGHT_GREEN)\n                else:\n                    self._out.writeln(\"    Remote: None\", Color.BRIGHT_GREEN)\n            url = getattr(conan, \"url\", None)\n            license_ = getattr(conan, \"license\", None)\n            author = getattr(conan, \"author\", None)\n            if url and show(\"url\"):\n                self._out.writeln(\"    URL: %s\" % url, Color.BRIGHT_GREEN)\n\n            if license_ and show(\"license\"):\n                if isinstance(license_, (list, tuple, set)):\n                    self._out.writeln(\"    Licenses: %s\" % \", \".join(license_), Color.BRIGHT_GREEN)\n                else:\n                    self._out.writeln(\"    License: %s\" % license_, Color.BRIGHT_GREEN)\n            if author and show(\"author\"):\n                self._out.writeln(\"    Author: %s\" % author, Color.BRIGHT_GREEN)\n\n            if isinstance(ref, ConanFileReference) and show(\"update\"):  # Excludes PROJECT\n                update = graph_updates_info.get(ref)\n                update_messages = {\n                 None: (\"Version not checked\", Color.WHITE),\n                 0: (\"You have the latest version (%s)\" % remote_name, Color.BRIGHT_GREEN),\n                 1: (\"There is a newer version (%s)\" % remote_name, Color.BRIGHT_YELLOW),\n                 -1: (\"The local file is newer than remote's one (%s)\" % remote_name,\n                      Color.BRIGHT_RED)\n                }\n                self._out.writeln(\"    Updates: %s\" % update_messages[update][0],\n                                  update_messages[update][1])\n\n            if node_times and node_times.get(ref, None) and show(\"date\"):\n                self._out.writeln(\"    Creation date: %s\" % node_times.get(ref, None),\n                                  Color.BRIGHT_GREEN)\n\n            dependants = deps_graph.inverse_neighbors(node)\n            if isinstance(ref, ConanFileReference) and show(\"required\"):  # Excludes\n                self._out.writeln(\"    Required by:\", Color.BRIGHT_GREEN)\n                for d in dependants:\n                    ref = d.conan_ref if d.conan_ref else project_reference\n                    self._out.writeln(\"        %s\" % str(ref), Color.BRIGHT_YELLOW)\n\n            if show(\"requires\"):\n                depends = deps_graph.neighbors(node)\n                if depends:\n                    self._out.writeln(\"    Requires:\", Color.BRIGHT_GREEN)\n                    for d in depends:\n                        self._out.writeln(\"        %s\" % repr(d.conan_ref), Color.BRIGHT_YELLOW)\n\n    def print_search_recipes(self, references, pattern, raw):\n        \"\"\" Print all the exported conans information\n        param pattern: wildcards, e.g., \"opencv/*\"\n        \"\"\"\n        if not references and not raw:\n            warn_msg = \"There are no packages\"\n            pattern_msg = \" matching the '%s' pattern\" % pattern\n            self._out.info(warn_msg + pattern_msg if pattern else warn_msg)\n            return\n\n        if not raw:\n            self._out.info(\"Existing package recipes:\\n\")\n            if isinstance(references, dict):\n                for remote, refs in references.items():\n                    self._out.highlight(\"Remote '%s':\" % str(remote))\n                    for conan_ref in sorted(refs):\n                        self._print_colored_line(str(conan_ref), indent=0)\n            else:\n                for conan_ref in sorted(references):\n                    self._print_colored_line(str(conan_ref), indent=0)\n        else:\n            if isinstance(references, dict):\n                for remote, refs in references.items():\n                    self._out.writeln(\"Remote '%s':\" % str(remote))\n                    for conan_ref in sorted(refs):\n                        self._out.writeln(str(conan_ref))\n            else:\n                self._out.writeln(\"\\n\".join([str(ref) for ref in references]))\n\n    def print_search_packages(self, packages_props, reference, recipe_hash, packages_query):\n        if not packages_props:\n            if packages_query:\n                warn_msg = \"There are no packages for reference '%s' matching the query '%s'\" % (str(reference),\n                                                                                                 packages_query)\n            else:\n                warn_msg = \"There are no packages for reference '%s'\" % str(reference)\n\n            if recipe_hash:\n                warn_msg += \", but package recipe found.\"\n\n            self._out.info(warn_msg)\n            return\n\n        self._out.info(\"Existing packages for recipe %s:\\n\" % str(reference))\n        # Each package\n        for package_id, properties in sorted(packages_props.items()):\n            self._print_colored_line(\"Package_ID\", package_id, 1)\n            for section in (\"options\", \"settings\", \"full_requires\"):\n                attrs = properties.get(section, [])\n                if attrs:\n                    section_name = {\"full_requires\": \"requires\"}.get(section, section)\n                    self._print_colored_line(\"[%s]\" % section_name, indent=2)\n                    if isinstance(attrs, dict):  # options, settings\n                        attrs = OrderedDict(sorted(attrs.items()))\n                        for key, value in attrs.items():\n                            self._print_colored_line(key, value=value, indent=3)\n                    elif isinstance(attrs, list):  # full requires\n                        for key in sorted(attrs):\n                            self._print_colored_line(key, indent=3)\n            package_recipe_hash = properties.get(\"recipe_hash\", None)\n            # Always compare outdated with local recipe, simplification,\n            # if a remote check is needed install recipe first\n            if recipe_hash:\n                self._print_colored_line(\"Outdated from recipe: %s\" % (recipe_hash != package_recipe_hash), indent=2)\n            self._out.writeln(\"\")\n\n    def print_profile(self, name, profile):\n        self._out.info(\"Configuration for profile %s:\\n\" % name)\n        self._print_profile_section(\"settings\", profile.settings.items(), separator=\"=\")\n        self._print_profile_section(\"options\", profile.options.as_list(), separator=\"=\")\n        self._print_profile_section(\"build_requires\", [(key, \", \".join(str(val) for val in values))\n                                                       for key, values in\n                                                       profile.build_requires.items()])\n\n        envs = []\n        for package, env_vars in profile.env_values.data.items():\n            for name, value in env_vars.items():\n                key = \"%s:%s\" % (package, name) if package else name\n                envs.append((key, value))\n        self._print_profile_section(\"env\", envs, separator='=')\n\n    def _print_profile_section(self, name, items, indent=0, separator=\": \"):\n        self._print_colored_line(\"[%s]\" % name, indent=indent, color=Color.BRIGHT_RED)\n        for key, value in items:\n            self._print_colored_line(key, value=str(value), indent=0, separator=separator)\n\n    def _print_colored_line(self, text, value=None, indent=0, separator=\": \", color=None):\n        \"\"\" Print a colored line depending on its indentation level\n            Attributes:\n                text: string line\n                split_symbol: if you want an output with different in-line colors\n                indent_plus: integer to add a plus indentation\n        \"\"\"\n        text = text.strip()\n        if not text:\n            return\n\n        text_color = Printer.INDENT_COLOR.get(indent, Color.BRIGHT_WHITE) if not color else color\n        indent_text = ' ' * Printer.INDENT_SPACES * indent\n        if value is not None:\n            value_color = Color.BRIGHT_WHITE\n            self._out.write('%s%s%s' % (indent_text, text, separator), text_color)\n            self._out.writeln(value, value_color)\n        else:\n            self._out.writeln('%s%s' % (indent_text, text), text_color)\n", "path": "conans/client/printer.py"}]}