# Path: harpoon/formatter.py
# class MergedOptionStringFormatter(MergedOptionStringFormatter):
#     """
#     Resolve format options into a MergedOptions dictionary
# 
#     Usage is like:
# 
#         configuration = MergedOptions.using({"numbers": "1 two {three}", "three": 3})
#         formatter = MergedOptionStringFormatter(configuration, "{numbers}")
#         val = formatter.format()
#         # val == "1 two 3"
# 
#     Where that second argument can be more than one format:
# 
#         configuration = MergedOptions.using({"one": 1, "two": 2, "three": 3})
#         formatter = MergedOptionStringFormatter(configuration, "{one} {two} {three}")
#         val = formatter.format()
#         # val == "1 2 3"
# 
#     The formatter also has a special feature where it returns the object it finds
#     if the string to be formatted is that one object::
# 
#         class dictsubclass(dict): pass
#         configuration = MergedOptions.using({"some_object": dictsubclass({1:2, 3:4})}, dont_prefix=[dictsubclass])
#         formatter = MergedOptionStringFormatter(configuration, "{some_object}")
#         val = formatter.format()
#         # val == {1:2, 3:4}
# 
#     For this to work, the object must be a subclass of dict and in the dont_prefix option of the configuration.
#     """
# 
#     passthrough_format_specs = ["env", "from_env"]
# 
#     def get_string(self, key):
#         """Get a string from all_options"""
#         # Make sure we special case the "content" option
#         if type(key) is str and key.startswith("content."):
#             return self.no_format(self.all_options["content"][key[8:]])
# 
#         if type(key) is list and len(key) == 2 and key[0] == "content":
#             return self.no_format(self.all_options[key])
# 
#         return super().get_string(key)
# 
#     def special_format_field(self, obj, format_spec):
#         """Know about any special formats"""
#         if format_spec == "env":
#             return "${{{0}}}".format(obj)
# 
#         elif format_spec == "from_env":
#             if obj not in os.environ:
#                 raise NoSuchEnvironmentVariable(wanted=obj)
#             return os.environ[obj]
# 
# Path: harpoon/errors.py
# class HarpoonError(DelfickError):
# class BadConfiguration(HarpoonError):
# class BadTask(HarpoonError):
# class BadOption(HarpoonError):
# class NoSuchKey(HarpoonError):
# class NoSuchImage(HarpoonError):
# class BadCommand(HarpoonError):
# class BadImage(HarpoonError):
# class CouldntKill(HarpoonError):
# class FailedImage(HarpoonError):
# class BadYaml(HarpoonError):
# class BadResult(HarpoonError):
# class UserQuit(HarpoonError):
# class BadDockerConnection(HarpoonError):
# class ImageDepCycle(HarpoonError):
# class BadDirectory(BadSpecValue):
# class BadFilename(BadSpecValue):
# class DeprecatedFeature(BadSpecValue):
# class BadEnvironment(HarpoonError):
# class BadAmazon(HarpoonError):
# class AlreadyBoundPorts(HarpoonError):
# class NoSuchEnvironmentVariable(HarpoonError):
# class FoundNoBoto(HarpoonError):
# 
# Path: harpoon/option_spec/command_objs.py
# class Command(dictobj):
#     """Holds a single command"""
# 
#     fields = [
#         "instruction",
#         ("extra_context", lambda: sb.NotSpecified),
#         ("extra", lambda: sb.NotSpecified),
#     ]
# 
#     def __repr__(self):
#         return "<Command({0})>".format(self.instruction)
# 
#     @property
#     def action(self):
#         return self._action
# 
#     @property
#     def dependent_image(self):
#         if self.action == "FROM":
#             return self.command
#         elif self.action == "ADD":
#             if self.extra_context is not sb.NotSpecified:
#                 options, _ = self.extra_context
#                 if hasattr(options, "image"):
#                     return options.image
#         elif self.action == "COPY":
#             if self.extra_context is not sb.NotSpecified:
#                 options, _ = self.extra_context
#                 if getattr(options, "image", sb.NotSpecified) is not sb.NotSpecified:
#                     return options.image
# 
#     @property
#     def instruction(self):
#         return self._instruction
# 
#     @instruction.setter
#     def instruction(self, val):
#         """Set the action and command from an instruction"""
#         self._instruction = val
#         if isinstance(val, tuple):
#             if len(val) == 2:
#                 self._action, self.command = val
#             else:
#                 self._action, self.command, self.extra = val
#         else:
#             split = val.split(" ", 1)
#             if split[0] == "FROM":
#                 split = val.split(" ", 2)
# 
#             if len(split) == 3:
#                 self._action, self.command, self.extra = split
#             else:
#                 self._action, self.command = split
# 
#     @property
#     def as_string(self):
#         """Return the command as a single string for the docker file"""
#         if type(self.instruction) is str:
#             return self.instruction
# 
#         if self.action == "FROM" and not isinstance(self.command, str):
#             extra = "" if self.extra is sb.NotSpecified else " {0}".format(self.extra)
#             return "{0} {1}{2}".format(self.action, self.command.from_name, extra)
#         else:
#             return "{0} {1}".format(self.action, self.command)


from harpoon.formatter import MergedOptionStringFormatter
from harpoon.errors import BadOption, ProgrammerError
from harpoon.option_spec.command_objs import Command
from delfick_project.norms import sb, BadSpecValue, dictobj, va, Validator
        from harpoon.option_spec.harpoon_specs import HarpoonSpec
        from harpoon.option_spec.image_objs import Image
        from harpoon.option_spec.harpoon_specs import HarpoonSpec
import hashlib
import json
"""
It's recommended you read this file from the bottom up.
"""





class CommandContentAddString(dictobj):
    fields = ["content"]

    def resolve(self):
        return self.content

    for_json = resolve


class CommandContent(dictobj):
    def setup(self, *args, **kwargs):
        if self.__class__ is CommandContent:

# Path: harpoon/formatter.py
# class MergedOptionStringFormatter(MergedOptionStringFormatter):
#     """
#     Resolve format options into a MergedOptions dictionary
# 
#     Usage is like:
# 
#         configuration = MergedOptions.using({"numbers": "1 two {three}", "three": 3})
#         formatter = MergedOptionStringFormatter(configuration, "{numbers}")
#         val = formatter.format()
#         # val == "1 two 3"
# 
#     Where that second argument can be more than one format:
# 
#         configuration = MergedOptions.using({"one": 1, "two": 2, "three": 3})
#         formatter = MergedOptionStringFormatter(configuration, "{one} {two} {three}")
#         val = formatter.format()
#         # val == "1 2 3"
# 
#     The formatter also has a special feature where it returns the object it finds
#     if the string to be formatted is that one object::
# 
#         class dictsubclass(dict): pass
#         configuration = MergedOptions.using({"some_object": dictsubclass({1:2, 3:4})}, dont_prefix=[dictsubclass])
#         formatter = MergedOptionStringFormatter(configuration, "{some_object}")
#         val = formatter.format()
#         # val == {1:2, 3:4}
# 
#     For this to work, the object must be a subclass of dict and in the dont_prefix option of the configuration.
#     """
# 
#     passthrough_format_specs = ["env", "from_env"]
# 
#     def get_string(self, key):
#         """Get a string from all_options"""
#         # Make sure we special case the "content" option
#         if type(key) is str and key.startswith("content."):
#             return self.no_format(self.all_options["content"][key[8:]])
# 
#         if type(key) is list and len(key) == 2 and key[0] == "content":
#             return self.no_format(self.all_options[key])
# 
#         return super().get_string(key)
# 
#     def special_format_field(self, obj, format_spec):
#         """Know about any special formats"""
#         if format_spec == "env":
#             return "${{{0}}}".format(obj)
# 
#         elif format_spec == "from_env":
#             if obj not in os.environ:
#                 raise NoSuchEnvironmentVariable(wanted=obj)
#             return os.environ[obj]
# 
# Path: harpoon/errors.py
# class HarpoonError(DelfickError):
# class BadConfiguration(HarpoonError):
# class BadTask(HarpoonError):
# class BadOption(HarpoonError):
# class NoSuchKey(HarpoonError):
# class NoSuchImage(HarpoonError):
# class BadCommand(HarpoonError):
# class BadImage(HarpoonError):
# class CouldntKill(HarpoonError):
# class FailedImage(HarpoonError):
# class BadYaml(HarpoonError):
# class BadResult(HarpoonError):
# class UserQuit(HarpoonError):
# class BadDockerConnection(HarpoonError):
# class ImageDepCycle(HarpoonError):
# class BadDirectory(BadSpecValue):
# class BadFilename(BadSpecValue):
# class DeprecatedFeature(BadSpecValue):
# class BadEnvironment(HarpoonError):
# class BadAmazon(HarpoonError):
# class AlreadyBoundPorts(HarpoonError):
# class NoSuchEnvironmentVariable(HarpoonError):
# class FoundNoBoto(HarpoonError):
# 
# Path: harpoon/option_spec/command_objs.py
# class Command(dictobj):
#     """Holds a single command"""
# 
#     fields = [
#         "instruction",
#         ("extra_context", lambda: sb.NotSpecified),
#         ("extra", lambda: sb.NotSpecified),
#     ]
# 
#     def __repr__(self):
#         return "<Command({0})>".format(self.instruction)
# 
#     @property
#     def action(self):
#         return self._action
# 
#     @property
#     def dependent_image(self):
#         if self.action == "FROM":
#             return self.command
#         elif self.action == "ADD":
#             if self.extra_context is not sb.NotSpecified:
#                 options, _ = self.extra_context
#                 if hasattr(options, "image"):
#                     return options.image
#         elif self.action == "COPY":
#             if self.extra_context is not sb.NotSpecified:
#                 options, _ = self.extra_context
#                 if getattr(options, "image", sb.NotSpecified) is not sb.NotSpecified:
#                     return options.image
# 
#     @property
#     def instruction(self):
#         return self._instruction
# 
#     @instruction.setter
#     def instruction(self, val):
#         """Set the action and command from an instruction"""
#         self._instruction = val
#         if isinstance(val, tuple):
#             if len(val) == 2:
#                 self._action, self.command = val
#             else:
#                 self._action, self.command, self.extra = val
#         else:
#             split = val.split(" ", 1)
#             if split[0] == "FROM":
#                 split = val.split(" ", 2)
# 
#             if len(split) == 3:
#                 self._action, self.command, self.extra = split
#             else:
#                 self._action, self.command = split
# 
#     @property
#     def as_string(self):
#         """Return the command as a single string for the docker file"""
#         if type(self.instruction) is str:
#             return self.instruction
# 
#         if self.action == "FROM" and not isinstance(self.command, str):
#             extra = "" if self.extra is sb.NotSpecified else " {0}".format(self.extra)
#             return "{0} {1}{2}".format(self.action, self.command.from_name, extra)
#         else:
#             return "{0} {1}".format(self.action, self.command)


# Path: harpoon/option_spec/command_specs.py
from harpoon.formatter import MergedOptionStringFormatter
from harpoon.errors import BadOption, ProgrammerError
from harpoon.option_spec.command_objs import Command
from delfick_project.norms import sb, BadSpecValue, dictobj, va, Validator
        from harpoon.option_spec.harpoon_specs import HarpoonSpec
        from harpoon.option_spec.image_objs import Image
        from harpoon.option_spec.harpoon_specs import HarpoonSpec
import hashlib
import json

"""
It's recommended you read this file from the bottom up.
"""





class CommandContentAddString(dictobj):
    fields = ["content"]

    def resolve(self):
        return self.content

    for_json = resolve


class CommandContent(dictobj):
    def setup(self, *args, **kwargs):
        if self.__class__ is CommandContent:

            raise ProgrammerError("This should never be instantiated without subclassing it")