public void readActionInputArguments(
     Element actionRequestElement, ActionInvocation actionInvocation) throws ActionException {
   actionInvocation.setInput(
       readArgumentValues(
           actionRequestElement.getChildNodes(),
           actionInvocation.getAction().getInputArguments()));
 }
  protected void writeFaultElement(
      Document d, Element bodyElement, ActionInvocation actionInvocation) {

    Element faultElement = d.createElementNS(Constants.SOAP_NS_ENVELOPE, "s:Fault");
    bodyElement.appendChild(faultElement);

    // This stuff is really completely arbitrary nonsense... let's hope they fired the guy who
    // decided this
    XMLUtil.appendNewElement(d, faultElement, "faultcode", "s:Client");
    XMLUtil.appendNewElement(d, faultElement, "faultstring", "UPnPError");

    Element detailElement = d.createElement("detail");
    faultElement.appendChild(detailElement);

    Element upnpErrorElement = d.createElementNS(Constants.NS_UPNP_CONTROL_10, "UPnPError");
    detailElement.appendChild(upnpErrorElement);

    int errorCode = actionInvocation.getFailure().getErrorCode();
    String errorDescription = actionInvocation.getFailure().getMessage();

    log.fine("Writing fault element: " + errorCode + " - " + errorDescription);

    XMLUtil.appendNewElement(d, upnpErrorElement, "errorCode", Integer.toString(errorCode));
    XMLUtil.appendNewElement(d, upnpErrorElement, "errorDescription", errorDescription);
  }
  public void success(ActionInvocation invocation) {
    log.fine("Successful browse action, reading output argument values");

    BrowseResult result =
        new BrowseResult(
            invocation.getOutput("Result").getValue().toString(),
            (UnsignedIntegerFourBytes) invocation.getOutput("NumberReturned").getValue(),
            (UnsignedIntegerFourBytes) invocation.getOutput("TotalMatches").getValue(),
            (UnsignedIntegerFourBytes) invocation.getOutput("UpdateID").getValue());

    boolean proceed = receivedRaw(invocation, result);

    if (proceed && result.getCountLong() > 0 && result.getResult().length() > 0) {

      try {

        DIDLParser didlParser = new DIDLParser();
        DIDLContent didl = didlParser.parse(result.getResult());
        received(invocation, didl);
        updateStatus(Status.OK);

      } catch (Exception ex) {
        invocation.setFailure(
            new ActionException(
                ErrorCode.ACTION_FAILED, "Can't parse DIDL XML response: " + ex, ex));
        failure(invocation, null);
      }

    } else {
      received(invocation, new DIDLContent());
      updateStatus(Status.NO_CONTENT);
    }
  }
  protected void readActionOutputArguments(
      Element actionResponseElement, ActionInvocation actionInvocation) throws ActionException {

    actionInvocation.setOutput(
        readArgumentValues(
            actionResponseElement.getChildNodes(),
            actionInvocation.getAction().getOutputArguments()));
  }
  protected void writeActionOutputArguments(
      Document d, Element actionResponseElement, ActionInvocation actionInvocation) {

    for (ActionArgument argument : actionInvocation.getAction().getOutputArguments()) {
      log.fine("Writing action output argument: " + argument.getName());
      String value =
          actionInvocation.getOutput(argument) != null
              ? actionInvocation.getOutput(argument).toString()
              : "";
      XMLUtil.appendNewElement(d, actionResponseElement, argument.getName(), value);
    }
  }
  protected Element writeActionResponseElement(
      Document d,
      Element bodyElement,
      ActionResponseMessage message,
      ActionInvocation actionInvocation) {

    log.fine("Writing action response element: " + actionInvocation.getAction().getName());
    Element actionResponseElement =
        d.createElementNS(
            message.getActionNamespace(),
            "u:" + actionInvocation.getAction().getName() + "Response");
    bodyElement.appendChild(actionResponseElement);

    return actionResponseElement;
  }
  public void writeBody(ActionResponseMessage responseMessage, ActionInvocation actionInvocation)
      throws UnsupportedDataException {

    log.fine("Writing body of " + responseMessage + " for: " + actionInvocation);

    try {

      DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
      factory.setNamespaceAware(true);
      Document d = factory.newDocumentBuilder().newDocument();
      Element body = writeBodyElement(d);

      if (actionInvocation.getFailure() != null) {
        writeBodyFailure(d, body, responseMessage, actionInvocation);
      } else {
        writeBodyResponse(d, body, responseMessage, actionInvocation);
      }

      if (log.isLoggable(Level.FINER)) {
        log.finer(
            "===================================== SOAP BODY BEGIN ============================================");
        log.finer(responseMessage.getBodyString());
        log.finer(
            "-===================================== SOAP BODY END ============================================");
      }

    } catch (Exception ex) {
      throw new UnsupportedDataException("Can't transform message payload: " + ex, ex);
    }
  }
  protected Element readActionRequestElement(
      Element bodyElement, ActionRequestMessage message, ActionInvocation actionInvocation) {
    NodeList bodyChildren = bodyElement.getChildNodes();

    log.fine(
        "Looking for action request element matching namespace:" + message.getActionNamespace());

    for (int i = 0; i < bodyChildren.getLength(); i++) {
      Node bodyChild = bodyChildren.item(i);

      if (bodyChild.getNodeType() != Node.ELEMENT_NODE) continue;

      String unprefixedName = getUnprefixedNodeName(bodyChild);
      if (unprefixedName.equals(actionInvocation.getAction().getName())) {
        if (bodyChild.getNamespaceURI() == null
            || !bodyChild.getNamespaceURI().equals(message.getActionNamespace()))
          throw new UnsupportedDataException(
              "Illegal or missing namespace on action request element: " + bodyChild);
        log.fine("Reading action request element: " + unprefixedName);
        return (Element) bodyChild;
      }
    }
    throw new UnsupportedDataException(
        "Could not read action request element matching namespace: "
            + message.getActionNamespace());
  }
  // Convenience functions for sending various upnp service requests
  public static ActionInvocation send(
      final Device dev, String instanceID, String service, String action, String... args) {
    Service svc = dev.findService(ServiceId.valueOf("urn:upnp-org:serviceId:" + service));
    final String uuid = getUUID(dev);
    if (svc != null) {
      Action x = svc.getAction(action);
      String name = getFriendlyName(dev);
      boolean log = !action.equals("GetPositionInfo");
      if (x != null) {
        ActionInvocation a = new ActionInvocation(x);
        a.setInput("InstanceID", instanceID);
        for (int i = 0; i < args.length; i += 2) {
          a.setInput(args[i], args[i + 1]);
        }
        if (log) {
          LOGGER.debug("Sending upnp {}.{} {} to {}[{}]", service, action, args, name, instanceID);
        }
        new ActionCallback(a, upnpService.getControlPoint()) {
          @Override
          public void success(ActionInvocation invocation) {
            rendererMap.mark(uuid, ACTIVE, true);
          }

          @Override
          public void failure(
              ActionInvocation invocation, UpnpResponse operation, String defaultMsg) {
            LOGGER.debug("Action failed: {}", defaultMsg);
            rendererMap.mark(uuid, ACTIVE, false);
          }
        }.run();

        if (log) {
          for (ActionArgumentValue arg : a.getOutput()) {
            LOGGER.debug(
                "Received from {}[{}]: {}={}",
                name,
                instanceID,
                arg.getArgument().getName(),
                arg.toString());
          }
        }
        return a;
      }
    }
    return null;
  }
示例#10
0
  @Test(dataProvider = "devices")
  public void invokeActions(LocalDevice device) {
    LocalService svc = device.getServices()[0];

    ActionInvocation setColor = new ActionInvocation(svc.getAction("SetColor"));
    setColor.setInput("In", MyServiceWithEnum.Color.Blue);
    svc.getExecutor(setColor.getAction()).execute(setColor);
    assertEquals(setColor.getFailure(), null);
    assertEquals(setColor.getOutput().length, 0);

    ActionInvocation getColor = new ActionInvocation(svc.getAction("GetColor"));
    svc.getExecutor(getColor.getAction()).execute(getColor);
    assertEquals(getColor.getFailure(), null);
    assertEquals(getColor.getOutput().length, 1);
    assertEquals(getColor.getOutput()[0].toString(), MyServiceWithEnum.Color.Blue.name());
  }
  protected Element readActionResponseElement(
      Element bodyElement, ActionInvocation actionInvocation) {
    NodeList bodyChildren = bodyElement.getChildNodes();

    for (int i = 0; i < bodyChildren.getLength(); i++) {
      Node bodyChild = bodyChildren.item(i);

      if (bodyChild.getNodeType() != Node.ELEMENT_NODE) continue;

      if (getUnprefixedNodeName(bodyChild)
          .equals(actionInvocation.getAction().getName() + "Response")) {
        log.fine("Reading action response element: " + getUnprefixedNodeName(bodyChild));
        return (Element) bodyChild;
      }
    }
    log.fine("Could not read action response element");
    return null;
  }
  public void readBody(ActionResponseMessage responseMsg, ActionInvocation actionInvocation)
      throws UnsupportedDataException {

    log.fine("Reading body of " + responseMsg + " for: " + actionInvocation);
    if (log.isLoggable(Level.FINER)) {
      log.finer(
          "===================================== SOAP BODY BEGIN ============================================");
      log.finer(responseMsg.getBodyString());
      log.finer(
          "-===================================== SOAP BODY END ============================================");
    }

    String body = getMessageBody(responseMsg);
    try {

      DocumentBuilderFactory factory = createDocumentBuilderFactory();
      factory.setNamespaceAware(true);
      DocumentBuilder documentBuilder = factory.newDocumentBuilder();
      documentBuilder.setErrorHandler(this);

      Document d = documentBuilder.parse(new InputSource(new StringReader(body)));

      Element bodyElement = readBodyElement(d);

      ActionException failure = readBodyFailure(d, bodyElement);

      if (failure == null) {
        readBodyResponse(d, bodyElement, responseMsg, actionInvocation);
      } else {
        actionInvocation.setFailure(failure);
      }

    } catch (Exception ex) {
      throw new UnsupportedDataException("Can't transform message payload: " + ex, ex, body);
    }
  }
 @Override
 public String convert(final ActionInvocation<RemoteService> invocation) {
   return (String) invocation.getOutput("NewExternalIPAddress").getValue();
 }