问:
How to make Amazon AWS API call from Java?
What are my options if I want to make a call to Amazon AWS Rest API from Java.

When implementing my own request, generating the AWS4-HMAC-SHA256 Authorization header would be the hardest.

Essentially, this is the header I need to generate:

```<code>Authorization: AWS4-HMAC-SHA256 Credential=AKIAJTOUYS27JPVRDUYQ/20200602/us-east-1/route53/aws4_request, SignedHeaders=host;x-amz-content-sha256;x-amz-date, Signature=ba85affa19fa4a8735ce952e50d41c8c93406a11d22b88cc98b109b529bcc15e
</code>```

答:
Not saying that this is a complete list, but I would consider using established libraries like:

Official AWS SDK v1, or v2 - current and comprehensive but depends on netty.io and many other jars.

Apache JClouds - depends on JAXB which is not longer a part of JDK but now available at maven central separately.

But sometimes, all you want is to make a simple call, and you don't want to bring many dependencies into your application. You may want to implement the rest call yourself. Generating the right AWS Authorization header is the hardest bit to implement.

Here is the code to do that in pure java OpenJDK with no external dependencies.

It implements Amazon AWS API Signature Version 4 signing process.

AmazonRequestSignatureV4Utils.java

package com.frusal.amazonsig4;

import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.util.*;
import java.util.Map.Entry;
import java.util.stream.Collectors;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;

/**
 * Copyright 2020 Alex Vasiliev, licensed under the Apache 2.0 license: https://opensource.org/licenses/Apache-2.0
 */
public class AmazonRequestSignatureV4Utils {

    /**
     * Generates signing headers for HTTP request in accordance with Amazon AWS API Signature version 4 process.
     *

     * Following steps outlined here: docs.aws.amazon.com
     *

     * Simple usage example is here: {@link AmazonRequestSignatureV4Example}
     *

     * This method takes many arguments as read-only, but adds necessary headers to @{code headers} argument, which is a map.
     * The caller should make sure those parameters are copied to the actual request object.
     *

     * The ISO8601 date parameter can be created by making a call to:

     * - {@code java.time.format.DateTimeFormatter.ofPattern("yyyyMMdd'T'HHmmss'Z'").format(ZonedDateTime.now(ZoneOffset.UTC))}

     * or, if you prefer joda:

     * - {@code org.joda.time.format.ISODateTimeFormat.basicDateTimeNoMillis().print(DateTime.now().withZone(DateTimeZone.UTC))}
     *
     * @param method - HTTP request method, (GET|POST|DELETE|PUT|...), e.g., {@link java.net.HttpURLConnection#getRequestMethod()}
     * @param host - URL host, e.g., {@link java.net.URL#getHost()}.
     * @param path - URL path, e.g., {@link java.net.URL#getPath()}.
     * @param query - URL query, (parameters in sorted order, see the AWS spec) e.g., {@link java.net.URL#getQuery()}.
     * @param headers - HTTP request header map. This map is going to have entries added to it by this method. Initially populated with
     *     headers to be included in the signature. Like often compulsory 'Host' header. e.g., {@link java.net.HttpURLConnection#getRequestProperties()}.
     * @param body - The binary request body, for requests like POST.
     * @param isoDateTime - The time and date of the request in ISO8601 basic format, see comment above.
     * @param awsIdentity - AWS Identity, e.g., "AKIAJTOUYS27JPVRDUYQ"
     * @param awsSecret - AWS Secret Key, e.g., "I8Q2hY819e+7KzBnkXj66n1GI9piV+0p3dHglAzQ"
     * @param awsRegion - AWS Region, e.g., "us-east-1"
     * @param awsService - AWS Service, e.g., "route53"
     */
    public static void calculateAuthorizationHeaders(
            String method, String host, String path, String query, Map<String, String> headers,
            byte[] body,
            String isoDateTime,
            String awsIdentity, String awsSecret, String awsRegion, String awsService
    ) {
        try {
            String bodySha256 = hex(sha256(body));
            String isoJustDate = isoDateTime.substring(0, 8); // Cut the date portion of a string like '20150830T123600Z';

            headers.put("Host", host);
            headers.put("X-Amz-Content-Sha256", bodySha256);
            headers.put("X-Amz-Date", isoDateTime);

            // (1) https://docs.aws.amazon.com/general/latest/gr/sigv4-create-canonical-request.html
            List<String> canonicalRequestLines = new ArrayList<>();
            canonicalRequestLines.add(method);
            canonicalRequestLines.add(path);
            canonicalRequestLines.add(query);
            List<String> hashedHeaders = new ArrayList<>();
            List<String> headerKeysSorted = headers.keySet().stream().sorted(Comparator.comparing(e -> e.toLowerCase(Locale.US))).collect(Collectors.toList());
            for (String key : headerKeysSorted) {
                hashedHeaders.add(key.toLowerCase(Locale.US));
                canonicalRequestLines.add(key.toLowerCase(Locale.US) + ":" + normalizeSpaces(headers.get(key)));
            }
            canonicalRequestLines.add(null); // new line required after headers
            String signedHeaders = hashedHeaders.stream().collect(Collectors.joining(";"));
            canonicalRequestLines.add(signedHeaders);
            canonicalRequestLines.add(bodySha256);
            String canonicalRequestBody = canonicalRequestLines.stream().map(line -> line == null ? "" : line).collect(Collectors.joining("\n"));
            String canonicalRequestHash = hex(sha256(canonicalRequestBody.getBytes(StandardCharsets.UTF_8)));

            // (2) https://docs.aws.amazon.com/general/latest/gr/sigv4-create-string-to-sign.html
            List<String> stringToSignLines = new ArrayList<>();
            stringToSignLines.add("AWS4-HMAC-SHA256");
            stringToSignLines.add(isoDateTime);
            String credentialScope = isoJustDate + "/" + awsRegion + "/" + awsService + "/aws4_request";
            stringToSignLines.add(credentialScope);
            stringToSignLines.add(canonicalRequestHash);
            String stringToSign = stringToSignLines.stream().collect(Collectors.joining("\n"));

            // (3) https://docs.aws.amazon.com/general/latest/gr/sigv4-calculate-signature.html
            byte[] kDate = hmac(("AWS4" + awsSecret).getBytes(StandardCharsets.UTF_8), isoJustDate);
            byte[] kRegion = hmac(kDate, awsRegion);
            byte[] kService = hmac(kRegion, awsService);
            byte[] kSigning = hmac(kService, "aws4_request");
            String signature = hex(hmac(kSigning, stringToSign));

            String authParameter = "AWS4-HMAC-SHA256 Credential=" + awsIdentity + "/" + credentialScope + ", SignedHeaders=" + signedHeaders + ", Signature=" + signature;
            headers.put("Authorization", authParameter);

        } catch (Exception e) {
            if (e instanceof RuntimeException) {
                throw (RuntimeException) e;
            } else {
                throw new IllegalStateException(e);
            }
        }
    }

    private static String normalizeSpaces(String value) {
        return value.replaceAll("\\s+", " ").trim();
    }

    public static String hex(byte[] a) {
        StringBuilder sb = new StringBuilder(a.length * 2);
        for(byte b: a) {
            sb.append(String.format("%02x", b));
        }
        return sb.toString();
     }

    private static byte[] sha256(byte[] bytes) throws Exception {
        MessageDigest digest = MessageDigest.getInstance("SHA-256");
        digest.update(bytes);
        return digest.digest();
    }

    public static byte[] hmac(byte[] key, String msg) throws Exception {
        Mac mac = Mac.getInstance("HmacSHA256");
        mac.init(new SecretKeySpec(key, "HmacSHA256"));
        return mac.doFinal(msg.getBytes(StandardCharsets.UTF_8));
    }

}
```

<p>And the usage example:</p>
AmazonRequestSignatureV4Utils.java
<pre class="lang-java prettyprint-override"><code>package com.frusal.amazonsig4;

import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.stream.Collectors;

public class AmazonRequestSignatureV4Example {

    public static void main(String[] args) throws Exception {
        String route53HostedZoneId = "Z08118721NNU878C4PBNA";
        String awsIdentity = "AKIAJTOUYS27JPVRDUYQ";
        String awsSecret = "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";
        String awsRegion = "us-east-1";
        String awsService = "route53";

        URL url = new URL("https://route53.amazonaws.com/2013-04-01/hostedzone/" + route53HostedZoneId + "/rrset");
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setRequestMethod("POST");
        System.out.println(connection.getRequestMethod() + " " + url);

        String body = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
                "<ChangeResourceRecordSetsRequest xmlns=\"https://route53.amazonaws.com/doc/2013-04-01/\">\n" +
                "<ChangeBatch>\n" +
                // " <Comment>optional comment about the changes in this change batch request</Comment>\n" +
                "   <Changes>\n" +
                "      <Change>\n" +
                "         <Action>UPSERT</Action>\n" +
                "         <ResourceRecordSet>\n" +
                "            <Name>c001cxxx.frusal.com.</Name>\n" +
                "            <Type>A</Type>\n" +
                "            <TTL>300</TTL>\n" +
                "            <ResourceRecords>\n" +
                "               <ResourceRecord>\n" +
                "                  <Value>157.245.232.185</Value>\n" +
                "               </ResourceRecord>\n" +
                "            </ResourceRecords>\n" +
                // " <HealthCheckId>optional ID of a Route 53 health check</HealthCheckId>\n" +
                "         </ResourceRecordSet>\n" +
                "      </Change>\n" +
                "   </Changes>\n" +
                "</ChangeBatch>\n" +
                "</ChangeResourceRecordSetsRequest>";
        byte[] bodyBytes = body.getBytes(StandardCharsets.UTF_8);

        Map<String, String> headers = new LinkedHashMap<>();
        String isoDate = DateTimeFormatter.ofPattern("yyyyMMdd'T'HHmmss'Z'").format(ZonedDateTime.now(ZoneOffset.UTC));
        AmazonRequestSignatureV4Utils.calculateAuthorizationHeaders(
                connection.getRequestMethod(),
                connection.getURL().getHost(),
                connection.getURL().getPath(),
                connection.getURL().getQuery(),
                headers,
                bodyBytes,
                isoDate,
                awsIdentity,
                awsSecret,
                awsRegion,
                awsService);

        // Unsigned headers
        headers.put("Content-Type", "text/xml; charset=utf-8"); // I guess it get modified somewhere on the way... Let's just leave it out of the signature.

        // Log headers and body
        System.out.println(headers.entrySet().stream().map(e -> e.getKey() + ": " + e.getValue()).collect(Collectors.joining("\n")));
        System.out.println(body);

        // Send
        headers.forEach((key, val) -> connection.setRequestProperty(key, val));
        connection.setDoOutput(true);
        connection.getOutputStream().write(bodyBytes);
        connection.getOutputStream().flush();

        int responseCode = connection.getResponseCode();
        System.out.println("connection.getResponseCode()=" + responseCode);

        String responseContentType = connection.getHeaderField("Content-Type");
        System.out.println("responseContentType=" + responseContentType);

        System.out.println("Response BODY:");
        if (connection.getErrorStream() != null) {
            System.out.println(new String(connection.getErrorStream().readAllBytes(), StandardCharsets.UTF_8));
        } else {
            System.out.println(new String(connection.getInputStream().readAllBytes(), StandardCharsets.UTF_8));
        }
    }
}
</code>```

And the trace it would generate:

POST https://route53.amazonaws.com/2013-04-01/hostedzone/Z08118721NNU878C4PBNA/rrset
Host: route53.amazonaws.com
X-Amz-Content-Sha256: 46c7521da55bcf9e99fa6e12ec83997fab53128b5df0fb12018a6b76fb2bf891
X-Amz-Date: 20200602T035618Z
Authorization: AWS4-HMAC-SHA256 Credential=AKIAJTOUYS27JPVRDUYQ/20200602/us-east-1/route53/aws4_request, SignedHeaders=host;x-amz-content-sha256;x-amz-date, Signature=6a59090f837cf71fa228d2650e9b82e9769e0ec13e9864e40bd2f81c682ef8cb
Content-Type: text/xml; charset=utf-8
<?xml version="1.0" encoding="UTF-8"?>
<ChangeResourceRecordSetsRequest xmlns="https://route53.amazonaws.com/doc/2013-04-01/">
<ChangeBatch>
   <Changes>
      <Change>
         <Action>UPSERT</Action>
         <ResourceRecordSet>
            <Name>c001cxxx.frusal.com.</Name>
            <Type>A</Type>
            <TTL>300</TTL>
            <ResourceRecords>
               <ResourceRecord>
                  <Value>157.245.232.185</Value>
               </ResourceRecord>
            </ResourceRecords>
         </ResourceRecordSet>
      </Change>
   </Changes>
</ChangeBatch>
</ChangeResourceRecordSetsRequest>
connection.getResponseCode()=200
responseContentType=text/xml
Response BODY:
<?xml version="1.0"?>
<ChangeResourceRecordSetsResponse xmlns="https://route53.amazonaws.com/doc/2013-04-01/"><ChangeInfo><Id>/change/C011827119UYGF04GVIP6</Id><Status>PENDING</Status><SubmittedAt>2020-06-02T03:56:25.822Z</SubmittedAt></ChangeInfo></ChangeResourceRecordSetsResponse>
```

Edit: Updated to sort the headers. Thanks @Gray for the find!

For the latest version of this code, please see java-amazon-request-signature-v4 repository at GitHub.

Body:
What are my options if I want to make a call to Amazon AWS Rest API from Java.

When implementing my own request, generating the AWS4-HMAC-SHA256 Authorization header would be the hardest.

Essentially, this is the header I need to generate:

Authorization: AWS4-HMAC-SHA256 Credential=AKIAJTOUYS27JPVRDUYQ/20200602/us-east-1/route53/aws4_request, SignedHeaders=host;x-amz-content-sha256;x-amz-date, Signature=ba85affa19fa4a8735ce952e50d41c8c93406a11d22b88cc98b109b529bcc15e

Body:
Not saying that this is a complete list, but I would consider using established libraries like:

Official AWS SDK v1, or v2 - current and comprehensive but depends on netty.io and many other jars.

Apache JClouds - depends on JAXB which is not longer a part of JDK but now available at maven central separately.

But sometimes, all you want is to make a simple call, and you don't want to bring many dependencies into your application. You may want to implement the rest call yourself. Generating the right AWS Authorization header is the hardest bit to implement.

Here is the code to do that in pure java OpenJDK with no external dependencies.

It implements Amazon AWS API Signature Version 4 signing process.

AmazonRequestSignatureV4Utils.java

package com.frusal.amazonsig4;

import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.util.*;
import java.util.Map.Entry;
import java.util.stream.Collectors;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;

/**
 * Copyright 2020 Alex Vasiliev, licensed under the Apache 2.0 license: https://opensource.org/licenses/Apache-2.0
 */
public class AmazonRequestSignatureV4Utils {

    /**
     * Generates signing headers for HTTP request in accordance with Amazon AWS API Signature version 4 process.
     * <p>
     * Following steps outlined here: <a href="https://docs.aws.amazon.com/general/latest/gr/signature-version-4.html">docs.aws.amazon.com</a>
     * <p>
     * Simple usage example is here: {@link AmazonRequestSignatureV4Example}
     * <p>
     * This method takes many arguments as read-only, but adds necessary headers to @{code headers} argument, which is a map.
     * The caller should make sure those parameters are copied to the actual request object.
     * <p>
     * The ISO8601 date parameter can be created by making a call to:<br>
     * - {@code java.time.format.DateTimeFormatter.ofPattern("yyyyMMdd'T'HHmmss'Z'").format(ZonedDateTime.now(ZoneOffset.UTC))}<br>
     * or, if you prefer joda:<br>
     * - {@code org.joda.time.format.ISODateTimeFormat.basicDateTimeNoMillis().print(DateTime.now().withZone(DateTimeZone.UTC))}
     *
     * @param method - HTTP request method, (GET|POST|DELETE|PUT|...), e.g., {@link java.net.HttpURLConnection#getRequestMethod()}
     * @param host - URL host, e.g., {@link java.net.URL#getHost()}.
     * @param path - URL path, e.g., {@link java.net.URL#getPath()}.
     * @param query - URL query, (parameters in sorted order, see the AWS spec) e.g., {@link java.net.URL#getQuery()}.
     * @param headers - HTTP request header map. This map is going to have entries added to it by this method. Initially populated with
     *     headers to be included in the signature. Like often compulsory 'Host' header. e.g., {@link java.net.HttpURLConnection#getRequestProperties()}.
     * @param body - The binary request body, for requests like POST.
     * @param isoDateTime - The time and date of the request in ISO8601 basic format, see comment above.
     * @param awsIdentity - AWS Identity, e.g., "AKIAJTOUYS27JPVRDUYQ"
     * @param awsSecret - AWS Secret Key, e.g., "I8Q2hY819e+7KzBnkXj66n1GI9piV+0p3dHglAzQ"
     * @param awsRegion - AWS Region, e.g., "us-east-1"
     * @param awsService - AWS Service, e.g., "route53"
     */
    public static void calculateAuthorizationHeaders(
            String method, String host, String path, String query, Map<String, String> headers,
            byte[] body,
            String isoDateTime,
            String awsIdentity, String awsSecret, String awsRegion, String awsService
    ) {
        try {
            String bodySha256 = hex(sha256(body));
            String isoJustDate = isoDateTime.substring(0, 8); // Cut the date portion of a string like '20150830T123600Z';

            headers.put("Host", host);
            headers.put("X-Amz-Content-Sha256", bodySha256);
            headers.put("X-Amz-Date", isoDateTime);

            // (1) https://docs.aws.amazon.com/general/latest/gr/sigv4-create-canonical-request.html
            List<String> canonicalRequestLines = new ArrayList<>();
            canonicalRequestLines.add(method);
            canonicalRequestLines.add(path);
            canonicalRequestLines.add(query);
            List<String> hashedHeaders = new ArrayList<>();
            List<String> headerKeysSorted = headers.keySet().stream().sorted(Comparator.comparing(e -> e.toLowerCase(Locale.US))).collect(Collectors.toList());
            for (String key : headerKeysSorted) {
                hashedHeaders.add(key.toLowerCase(Locale.US));
                canonicalRequestLines.add(key.toLowerCase(Locale.US) + ":" + normalizeSpaces(headers.get(key)));
            }
            canonicalRequestLines.add(null); // new line required after headers
            String signedHeaders = hashedHeaders.stream().collect(Collectors.joining(";"));
            canonicalRequestLines.add(signedHeaders);
            canonicalRequestLines.add(bodySha256);
            String canonicalRequestBody = canonicalRequestLines.stream().map(line -> line == null ? "" : line).collect(Collectors.joining("\n"));
            String canonicalRequestHash = hex(sha256(canonicalRequestBody.getBytes(StandardCharsets.UTF_8)));

            // (2) https://docs.aws.amazon.com/general/latest/gr/sigv4-create-string-to-sign.html
            List<String> stringToSignLines = new ArrayList<>();
            stringToSignLines.add("AWS4-HMAC-SHA256");
            stringToSignLines.add(isoDateTime);
            String credentialScope = isoJustDate + "/" + awsRegion + "/" + awsService + "/aws4_request";
            stringToSignLines.add(credentialScope);
            stringToSignLines.add(canonicalRequestHash);
            String stringToSign = stringToSignLines.stream().collect(Collectors.joining("\n"));

            // (3) https://docs.aws.amazon.com/general/latest/gr/sigv4-calculate-signature.html
            byte[] kDate = hmac(("AWS4" + awsSecret).getBytes(StandardCharsets.UTF_8), isoJustDate);
            byte[] kRegion = hmac(kDate, awsRegion);
            byte[] kService = hmac(kRegion, awsService);
            byte[] kSigning = hmac(kService, "aws4_request");
            String signature = hex(hmac(kSigning, stringToSign));

            String authParameter = "AWS4-HMAC-SHA256 Credential=" + awsIdentity + "/" + credentialScope + ", SignedHeaders=" + signedHeaders + ", Signature=" + signature;
            headers.put("Authorization", authParameter);

        } catch (Exception e) {
            if (e instanceof RuntimeException) {
                throw (RuntimeException) e;
            } else {
                throw new IllegalStateException(e);
            }
        }
    }

    private static String normalizeSpaces(String value) {
        return value.replaceAll("\\s+", " ").trim();
    }

    public static String hex(byte[] a) {
        StringBuilder sb = new StringBuilder(a.length * 2);
        for(byte b: a) {
            sb.append(String.format("%02x", b));
        }
        return sb.toString();
     }

    private static byte[] sha256(byte[] bytes) throws Exception {
        MessageDigest digest = MessageDigest.getInstance("SHA-256");
        digest.update(bytes);
        return digest.digest();
    }

    public static byte[] hmac(byte[] key, String msg) throws Exception {
        Mac mac = Mac.getInstance("HmacSHA256");
        mac.init(new SecretKeySpec(key, "HmacSHA256"));
        return mac.doFinal(msg.getBytes(StandardCharsets.UTF_8));
    }

}

And the usage example:

AmazonRequestSignatureV4Utils.java

package com.frusal.amazonsig4;

import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.stream.Collectors;

public class AmazonRequestSignatureV4Example {

    public static void main(String[] args) throws Exception {
        String route53HostedZoneId = "Z08118721NNU878C4PBNA";
        String awsIdentity = "AKIAJTOUYS27JPVRDUYQ";
        String awsSecret = "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";
        String awsRegion = "us-east-1";
        String awsService = "route53";

        URL url = new URL("https://route53.amazonaws.com/2013-04-01/hostedzone/" + route53HostedZoneId + "/rrset");
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setRequestMethod("POST");
        System.out.println(connection.getRequestMethod() + " " + url);

        String body = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
                "<ChangeResourceRecordSetsRequest xmlns=\"https://route53.amazonaws.com/doc/2013-04-01/\">\n" +
                "<ChangeBatch>\n" +
                // " <Comment>optional comment about the changes in this change batch request</Comment>\n" +
                "   <Changes>\n" +
                "      <Change>\n" +
                "         <Action>UPSERT</Action>\n" +
                "         <ResourceRecordSet>\n" +
                "            <Name>c001cxxx.frusal.com.</Name>\n" +
                "            <Type>A</Type>\n" +
                "            <TTL>300</TTL>\n" +
                "            <ResourceRecords>\n" +
                "               <ResourceRecord>\n" +
                "                  <Value>157.245.232.185</Value>\n" +
                "               </ResourceRecord>\n" +
                "            </ResourceRecords>\n" +
                // " <HealthCheckId>optional ID of a Route 53 health check</HealthCheckId>\n" +
                "         </ResourceRecordSet>\n" +
                "      </Change>\n" +
                "   </Changes>\n" +
                "</ChangeBatch>\n" +
                "</ChangeResourceRecordSetsRequest>";
        byte[] bodyBytes = body.getBytes(StandardCharsets.UTF_8);

        Map<String, String> headers = new LinkedHashMap<>();
        String isoDate = DateTimeFormatter.ofPattern("yyyyMMdd'T'HHmmss'Z'").format(ZonedDateTime.now(ZoneOffset.UTC));
        AmazonRequestSignatureV4Utils.calculateAuthorizationHeaders(
                connection.getRequestMethod(),
                connection.getURL().getHost(),
                connection.getURL().getPath(),
                connection.getURL().getQuery(),
                headers,
                bodyBytes,
                isoDate,
                awsIdentity,
                awsSecret,
                awsRegion,
                awsService);

        // Unsigned headers
        headers.put("Content-Type", "text/xml; charset=utf-8"); // I guess it get modified somewhere on the way... Let's just leave it out of the signature.

        // Log headers and body
        System.out.println(headers.entrySet().stream().map(e -> e.getKey() + ": " + e.getValue()).collect(Collectors.joining("\n")));
        System.out.println(body);

        // Send
        headers.forEach((key, val) -> connection.setRequestProperty(key, val));
        connection.setDoOutput(true);
        connection.getOutputStream().write(bodyBytes);
        connection.getOutputStream().flush();

        int responseCode = connection.getResponseCode();
        System.out.println("connection.getResponseCode()=" + responseCode);

        String responseContentType = connection.getHeaderField("Content-Type");
        System.out.println("responseContentType=" + responseContentType);

        System.out.println("Response BODY:");
        if (connection.getErrorStream() != null) {
            System.out.println(new String(connection.getErrorStream().readAllBytes(), StandardCharsets.UTF_8));
        } else {
            System.out.println(new String(connection.getInputStream().readAllBytes(), StandardCharsets.UTF_8));
        }
    }
}

And the trace it would generate:

POST https://route53.amazonaws.com/2013-04-01/hostedzone/Z08118721NNU878C4PBNA/rrset
Host: route53.amazonaws.com
X-Amz-Content-Sha256: 46c7521da55bcf9e99fa6e12ec83997fab53128b5df0fb12018a6b76fb2bf891
X-Amz-Date: 20200602T035618Z
Authorization: AWS4-HMAC-SHA256 Credential=AKIAJTOUYS27JPVRDUYQ/20200602/us-east-1/route53/aws4_request, SignedHeaders=host;x-amz-content-sha256;x-amz-date, Signature=6a59090f837cf71fa228d2650e9b82e9769e0ec13e9864e40bd2f81c682ef8cb
Content-Type: text/xml; charset=utf-8
<?xml version="1.0" encoding="UTF-8"?>
<ChangeResourceRecordSetsRequest xmlns="https://route53.amazonaws.com/doc/2013-04-01/">
<ChangeBatch>
   <Changes>
      <Change>
         <Action>UPSERT</Action>
         <ResourceRecordSet>
            <Name>c001cxxx.frusal.com.</Name>
            <Type>A</Type>
            <TTL>300</TTL>
            <ResourceRecords>
               <ResourceRecord>
                  <Value>157.245.232.185</Value>
               </ResourceRecord>
            </ResourceRecords>
         </ResourceRecordSet>
      </Change>
   </Changes>
</ChangeBatch>
</ChangeResourceRecordSetsRequest>
connection.getResponseCode()=200
responseContentType=text/xml
Response BODY:
<?xml version="1.0"?>
<ChangeResourceRecordSetsResponse xmlns="https://route53.amazonaws.com/doc/2013-04-01/"><ChangeInfo><Id>/change/C011827119UYGF04GVIP6</Id><Status>PENDING</Status><SubmittedAt>2020-06-02T03:56:25.822Z</SubmittedAt></ChangeInfo></ChangeResourceRecordSetsResponse>

Edit: Updated to sort the headers. Thanks @Gray for the find!

For the latest version of this code, please see java-amazon-request-signature-v4 repository at GitHub.


来源: stackexchange

问:
How to count the number of times a certain SSN number is occuring in a particular cell in a dataframe
I have a dataframe column with random unstructured entries. I need to count the number of times the SSN numbers are appearing in a particular cell.
Consider the below example as entries in a dataframe column:

the SSN 569-458-555 has to be replaced by 8965-78-698

SSN:25-965-9654 has to be coverage of$59 and 8968-65965 of $85

please find SSN#256-8695-65

payment completed for SSN= 569856-548, 55866-89-96,56478-9658

Output:

2

2

1

3

答:
Text used as input

```<code>Text
the SSN 569-458-555 has to be replaced by 8965-78-698
SSN:25-965-9654 has to be coverage of$59 and 8968-65965 of $85
please find SSN#256-8695-65
payment completed for SSN= 569856-548, 55866-89-96,56478-9658
</code>```

```<code>import pandas as pd
import re

df = pd.read_csv("data.csv", sep="\n")
print(df)

# convert to nine-digit number in the format "AAA-GG-SSSS"
def format_ssn(x):
    ssn_l = []
    for ssn in x:
        res = re.split(r"(\d{3})(\d{2})(\d{4})", ssn)
        # res[1:-1] clear empty matches from begin/end of string
        ssn_l.append("-".join(res[1:-1]))
    return ssn_l

dft = df["Text"].str.replace("-", "")
df["Count"] = dft.str.count(pat="(\d{9})")

df["SSNs"] = dft.str.findall(pat=r"(\d{9})")
df["SSNs"] = df["SSNs"].apply(lambda x: format_ssn(x))

print(df)
</code>```

Output from df

```<code>                                         Text  Count                                     SSNs
0  the SSN 569-458-555 has to be replaced ...      2               [569-45-8555, 896-57-8698]
1  SSN:25-965-9654 has to be coverage of$5...      2               [259-65-9654, 896-86-5965]
2                        please find SSN#2...      1                            [256-86-9565]
3  payment completed for SSN= 569856-548, ...      3  [569-85-6548, 558-66-8996, 564-78-9658]
</code>```

ContentLicense: CC BY-SA 4.0

Body:
Text used as input

Text
the SSN 569-458-555 has to be replaced by 8965-78-698
SSN:25-965-9654 has to be coverage of$59 and 8968-65965 of $85
please find SSN#256-8695-65
payment completed for SSN= 569856-548, 55866-89-96,56478-9658

import pandas as pd
import re

df = pd.read_csv("data.csv", sep="\n")
print(df)

# convert to nine-digit number in the format "AAA-GG-SSSS"
def format_ssn(x):
    ssn_l = []
    for ssn in x:
        res = re.split(r"(\d{3})(\d{2})(\d{4})", ssn)
        # res[1:-1] clear empty matches from begin/end of string
        ssn_l.append("-".join(res[1:-1]))
    return ssn_l

dft = df["Text"].str.replace("-", "")
df["Count"] = dft.str.count(pat="(\d{9})")

df["SSNs"] = dft.str.findall(pat=r"(\d{9})")
df["SSNs"] = df["SSNs"].apply(lambda x: format_ssn(x))

print(df)

Output from df

                                         Text  Count                                     SSNs
0  the SSN 569-458-555 has to be replaced ...      2               [569-45-8555, 896-57-8698]
1  SSN:25-965-9654 has to be coverage of$5...      2               [259-65-9654, 896-86-5965]
2                        please find SSN#2...      1                            [256-86-9565]
3  payment completed for SSN= 569856-548, ...      3  [569-85-6548, 558-66-8996, 564-78-9658]


问:
How do you kill a process and its children on a timeout in Go code?
I have a situation where I need to kill a process after some time. I start the process and then:

```<code>case <-time.After(timeout):
        if err := cmd.Process.Kill(); err != nil {
            return 0, fmt.Errorf("Failed to kill process: %v", err)
        }
</code>```

kills the process. But it only kills the parent process not the 5-10 child processes that main process starts. I also tried creating a process group and then doing:

```<code>syscall.Kill(-cmd.Process.Pid, syscall.SIGKILL)
</code>```

to kill main and grandchild processes, but not working. Is there any other way I can kill the processes.

答:
It is not clear whether you have control of those child processes. If so, you could consider using the following Linux feature (you also don't say whether it's specific to an OS).

This line of code asks the kernel to send a SIGHUP to the children when the parent's die. That way your Go process can just kill the parent and it will automatically kill all the children. Not only that, it never fails! The kernel is really good on that one.

```<code>prctl(PR_SET_PDEATHSIG, SIGHUP);
</code>```

Of course, there is a race condition if you do just that. That is, by the time the child calls this prctl() function, the parent may have died already in which case the child needs to exit immediately.

```<code>if(getppid() != parent_pid)
{
    exit(1);
}
</code>```

So the complete code to avoid the race condition is:

```<code>// must happen before the fork() call
const pid_t parent_pid = getpid();

const pid_t child_pid = fork();

if(child_pid != 0)
{
    // fork() failed (child_pid == -1) or worked (an actual PID)
    ...
    return;
}

prctl(PR_SET_PDEATHSIG, SIGHUP);

if(getppid() != parent_pid)
{
    exit(1);
}
</code>```

Note: it is customary to use SIGHUP for this situation. You may want to consider other signals too, especially if the children deal with pipes/sockets (in which case you are likely to ignore SIGHUP!) or need to handle SIGHUP for other reasons.

Now if you do not have any control over the code of the children processes... you could try to kill each one from your Go application by searching all the children, killing them one by one, and then kill the parent process. However, you always have a race condition that you can't avoid unless you can prevent that whole tree of children from creating new processes. If you can do that, then it's just a matter of registering the PID of all those children and killing them one by one.

Of course, if you can create a group, much better. Like the SIGHUP above, killing all the members of a group is done by the kernel and it won't miss any processes.

Body:
I have a situation where I need to kill a process after some time. I start the process and then:

case <-time.After(timeout):
        if err := cmd.Process.Kill(); err != nil {
            return 0, fmt.Errorf("Failed to kill process: %v", err)
        }

kills the process. But it only kills the parent process not the 5-10 child processes that main process starts. I also tried creating a process group and then doing:

syscall.Kill(-cmd.Process.Pid, syscall.SIGKILL)

to kill main and grandchild processes, but not working. Is there any other way I can kill the processes.

Body:
It is not clear whether you have control of those child processes. If so, you could consider using the following Linux feature (you also don't say whether it's specific to an OS).

This line of code asks the kernel to send a SIGHUP to the children when the parent's die. That way your Go process can just kill the parent and it will automatically kill all the children. Not only that, it never fails! The kernel is really good on that one.

prctl(PR_SET_PDEATHSIG, SIGHUP);

Of course, there is a race condition if you do just that. That is, by the time the child calls this prctl() function, the parent may have died already in which case the child needs to exit immediately.

if(getppid() != parent_pid)
{
    exit(1);
}

So the complete code to avoid the race condition is:

// must happen before the fork() call
const pid_t parent_pid = getpid();

const pid_t child_pid = fork();

if(child_pid != 0)
{
    // fork() failed (child_pid == -1) or worked (an actual PID)
    ...
    return;
}

prctl(PR_SET_PDEATHSIG, SIGHUP);

if(getppid() != parent_pid)
{
    exit(1);
}

Note: it is customary to use SIGHUP for this situation. You may want to consider other signals too, especially if the children deal with pipes/sockets (in which case you are likely to ignore SIGHUP!) or need to handle SIGHUP for other reasons.

Now if you do not have any control over the code of the children processes... you could try to kill each one from your Go application by searching all the children, killing them one by one, and then kill the parent process. However, you always have a race condition that you can't avoid unless you can prevent that whole tree of children from creating new processes. If you can do that, then it's just a matter of registering the PID of all those children and killing them one by one.

Of course, if you can create a group, much better. Like the SIGHUP above, killing all the members of a group is done by the kernel and it won't miss any processes.


问:
How to update other CoreData when onDelete occurs in a ForEach?
There two entities Parent and Child, which is one to many relationship. One Parent and many Child.

I use EditMode to delete Child data like:

```<code>@ObservedObject private var db = CoreDataDB<Child>(predicate: "parent")

var body: some View {

    VStack {
        Form {

            Section(header: Text("Title")) {
                ForEach(db.loadDB(relatedTo: parent)) { child in

                    if self.editMode == .active {
                        ChildListCell(name: child.name, order: child.order)
                    } else {
                        ...
                    }
                }
                .onDelete(perform: self.db.deleting)   <--- How to update CoreData when delete occurs in this line
            }
        }
    }
}
</code>```

The deleting method is defined in another Class like:

```<code>public func deleting(at indexset: IndexSet) {

    CoreData.executeBlockAndCommit {

        for index in indexset {
            CoreData.stack.context.delete(self.fetchedObjects[index])
        }
    }
}
</code>```

And I also want to update other Attribute of Parent and Child Entities when onDelete occurs. How to make it?

Thanks for any help.

答:
Here is possible approach</p>

```<code>Section(header: Text("Title")) {
    ForEach(db.loadDB(relatedTo: parent)) { child in

        if self.editMode == .active {
            ChildListCell(name: child.name, order: child.order)
        } else {
            ...
        }
    }
    .onDelete { indices in
      // make other update here ...

      self.db.deleting(at: indices)

      // ... or here
    }
}
</code>```

Body:
There two entities Parent and Child, which is one to many relationship. One Parent and many Child.

I use EditMode to delete Child data like:

@ObservedObject private var db = CoreDataDB<Child>(predicate: "parent")

var body: some View {

    VStack {
        Form {

            Section(header: Text("Title")) {
                ForEach(db.loadDB(relatedTo: parent)) { child in

                    if self.editMode == .active {
                        ChildListCell(name: child.name, order: child.order)
                    } else {
                        ...
                    }
                }
                .onDelete(perform: self.db.deleting)   <--- How to update CoreData when delete occurs in this line
            }
        }
    }
}

The deleting method is defined in another Class like:

public func deleting(at indexset: IndexSet) {

    CoreData.executeBlockAndCommit {

        for index in indexset {
            CoreData.stack.context.delete(self.fetchedObjects[index])
        }
    }
}

And I also want to update other Attribute of Parent and Child Entities when onDelete occurs. How to make it?

Thanks for any help.

Body:
Here is possible approach

Section(header: Text("Title")) {
    ForEach(db.loadDB(relatedTo: parent)) { child in

        if self.editMode == .active {
            ChildListCell(name: child.name, order: child.order)
        } else {
            ...
        }
    }
    .onDelete { indices in
      // make other update here ...

      self.db.deleting(at: indices)

      // ... or here
    }
}


问:
Does MS T-SQL include a data type called varchar2? and if so, what's the difference between it and between varchar?
Had this question in an interview. </p>

答:
No.  varchar2 is an Oracle datatype, equivalent to its (as well as TSQL's) own varchar.

CLARIFICATION

The differentiation between Oracle's varchar and varchar2 seems to have originated back when the ANSI SQL standard was still being formulated.  I cannot locate any definitive references as to what exactly the implementation differences, if any, were initially (pre-Oracle 7), as this remains a source of confusion.  Suffices to say that the two are practically treated as synonyms since Oracle 7.  Both suffered improvements (maximum size went from 2k to 4k) in release 8.  Note that TSQL's varchar can store 8k.

ContentLicense: CC BY-SA 2.5

Body: Had this question in an interview.

LastEditorDisplayName: MikeW

OwnerDisplayName: Vlad Romascanu

ContentLicense: CC BY-SA 3.0

LastEditorDisplayName: Vlad Romascanu


问:
OutOfMemory error while joining large images
I am joining two images using the code below but it throws an OutOfMemory error my images are around 1MB each.

```<code>private Bitmap overlayMark(String first, String second)
{
    Bitmap bmp1, bmp2;
    bmp1 = BitmapFactory.decodeFile(first);
    bmp2 = BitmapFactory.decodeFile(second);
    if (bmp1 == null || bmp2 == null)
        return bmp1;

    int height = bmp1.getHeight();
    if (height < bmp2.getHeight())
        height = bmp2.getHeight();

    Bitmap bmOverlay = Bitmap.createBitmap(bmp1.getWidth() + bmp2.getWidth(), height,
            Bitmap.Config.ARGB_8888);// Out of memory
    Canvas canvas = new Canvas(bmOverlay);
    canvas.drawBitmap(bmp1, 0, 0, null);
    canvas.drawBitmap(bmp2, bmp1.getWidth(), 0, null);
    bmp1.recycle();
    bmp2.recycle();
    return bmOverlay;
}
</code>```

Update: I tried below two answers but it still not allwoing me to create bitmap of such big size the problem is that the resultant bitmap is too large in size around 2400x3200 so its going out of memory.

How can I join large images without running out of memory?

答:
Without loading the image into memory, you CAN get the size of the image, using inJustDecodeBounds. The Bitmap returns null, but all the parameters are set. You can scale down the image accordingly.

If your JPEG images are 1 MiB each, conversion to a BMP will take a lot of memory indeed. You can easily calculate its BMP equivalent by the dimensions of the image. Conversion of such a large image is expected to crash indeed. Android limits its apps to 16 MiB VM only.

Also use RGB_565 instead of ARGB_8888.

So your only solution is:
(a) To use BitmapFactory.Options.inSampleSize to scale down the image
or
(b) Use Android NDK where the 16 MiB limit isn't there.

Body:
I am joining two images using the code below but it throws an OutOfMemory error my images are around 1MB each.

private Bitmap overlayMark(String first, String second)
{
    Bitmap bmp1, bmp2;
    bmp1 = BitmapFactory.decodeFile(first);
    bmp2 = BitmapFactory.decodeFile(second);
    if (bmp1 == null || bmp2 == null)
        return bmp1;

    int height = bmp1.getHeight();
    if (height < bmp2.getHeight())
        height = bmp2.getHeight();

    Bitmap bmOverlay = Bitmap.createBitmap(bmp1.getWidth() + bmp2.getWidth(), height,
            Bitmap.Config.ARGB_8888);// Out of memory
    Canvas canvas = new Canvas(bmOverlay);
    canvas.drawBitmap(bmp1, 0, 0, null);
    canvas.drawBitmap(bmp2, bmp1.getWidth(), 0, null);
    bmp1.recycle();
    bmp2.recycle();
    return bmOverlay;
}

Update: I tried below two answers but it still not allwoing me to create bitmap of such big size the problem is that the resultant bitmap is too large in size around 2400x3200 so its going out of memory.

How can I join large images without running out of memory?


问:
Stop pulling data from an API after a specific amount of time
I am pulling some data from a streaming API using python v3, I need to stop pulling that data after 60 seconds. Also if anyone has suggestions on chunk_size or some alternative for streaming I'd be open to that.
So far this is what I have:</p>

```<code>response = requests.get('link to site', stream=True)

for data in response.iter_content(chunk_size=100):
    print(data)
</code>```

答:
More speculation than answer, but you could set a timer and then close the response. This may do it but I don't have a good way to test it. I don't know which exception to expect when the response is closed so I catch them all and print so the code can be changed. </p>

```<code>import threading

response = requests.get('link to site', stream=True)
timer = threading.Timer(60, response.close)
try:
    timer.start()
    for data in response.iter_content(chunk_size=100):
        print(data)
    except Exception as e:
        print("you want to catch this", e)
finally:
    timer.cancel()
</code>```

Body:
I am pulling some data from a streaming API using python v3, I need to stop pulling that data after 60 seconds. Also if anyone has suggestions on chunk_size or some alternative for streaming I'd be open to that.
So far this is what I have:

response = requests.get('link to site', stream=True)

for data in response.iter_content(chunk_size=100):
    print(data)

Body:
More speculation than answer, but you could set a timer and then close the response. This may do it but I don't have a good way to test it. I don't know which exception to expect when the response is closed so I catch them all and print so the code can be changed.

import threading

response = requests.get('link to site', stream=True)
timer = threading.Timer(60, response.close)
try:
    timer.start()
    for data in response.iter_content(chunk_size=100):
        print(data)
    except Exception as e:
        print("you want to catch this", e)
finally:
    timer.cancel()


问:
what happen with my componentDidUpdate in reactjs?

this is file app.js

```<code>...
constructor(props) {
    super(props);
    this.state = {
      todoLists: [],
      inputValue: "",
      currentName: "",
      todoSearch: "",
      idUpdate: "",
      loader: true
    };
  }
 componentDidUpdate(){
    this.setState({
      loader: true
    })
  }
  componentDidMount() {
    axios
      .get("https://5ec912d99ccbaf0016aa8b6f.mockapi.io/todoLists")
      .then((res) => {
        this.setState({
          loader: false,
          todoLists: res.data
        });
      });
  }
...
</code>```

i added componentDidUpdate in my App but it message :  Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.

答:
componentDidUpdate Call every time when set state happen so, you have to remove setState in didUpdate or call based on condition  like this ..</p>

```<code>componentDidupdate(){
 //check this is called every time when render executed .
 console.log('did update');
  if(some condition){
   this.setState({});
 }
}
</code>```

Body:
this is file app.js

...
constructor(props) {
    super(props);
    this.state = {
      todoLists: [],
      inputValue: "",
      currentName: "",
      todoSearch: "",
      idUpdate: "",
      loader: true
    };
  }
 componentDidUpdate(){
    this.setState({
      loader: true
    })
  }
  componentDidMount() {
    axios
      .get("https://5ec912d99ccbaf0016aa8b6f.mockapi.io/todoLists")
      .then((res) => {
        this.setState({
          loader: false,
          todoLists: res.data
        });
      });
  }
...

i added componentDidUpdate in my App but it message :  Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.

Body:
componentDidUpdate Call every time when set state happen so, you have to remove setState in didUpdate or call based on condition  like this ..

componentDidupdate(){
 //check this is called every time when render executed .
 console.log('did update');
  if(some condition){
   this.setState({});
 }
}


问:
Error : Unable to start png() device
I am using Windows. When trying to plot a graph on png device, it fails with the error.

My code:

```<code>png("C:\\plot1.png", width = 480, height = 480, units = "px", bg = "white")

par(mar= c(4, 4, 2, 1))

hist(pwrcon$Global_active_power,col = "red", main = "Global Active Power", xlab = "Global Active Power (kilowatts)")

dev.off()
</code>```

Error:

```<code>Error in png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  unable to start png() device
In addition: Warning messages:
1: In png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  unable to open file 'C:\plot1.png' for writing
2: In png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  opening device failed
</code>```

Can anyone help me in getting this resolved?

Thanks in advance

答:
I added "dev.off()
"before plot, the problem solved. The reason may be because of the previous device has not turn off yet. </p>

Title: Error : Unable to start png() device

Body:
I am using Windows. When trying to plot a graph on png device, it fails with the error.

My code:

png("C:\\plot1.png", width = 480, height = 480, units = "px", bg = "white")

par(mar= c(4, 4, 2, 1))

hist(pwrcon$Global_active_power,col = "red", main = "Global Active Power", xlab = "Global Active Power (kilowatts)")

dev.off()

Error:

Error in png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  unable to start png() device
In addition: Warning messages:
1: In png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  unable to open file 'C:\plot1.png' for writing
2: In png("C:\\plot1.png", width = 480, height = 480, units = "px",  :
  opening device failed

Can anyone help me in getting this resolved?

Thanks in advance


问:
Passing argument to a flask GET function
I'm trying to write a simple messaging function and, despite searching, having trouble coming up with a workable solution. On the get function, the code retrieves stored messages and passes this to be rendered.

The post function stores the message which all works fine, however I'm trying to redirect the user back to the original page they came from to display the new message, hence trying to pass the receiving user variable to the get function.

My code so far below. I'm new to flask so would appreciate any other pointers as well. Thanks in advance!

```<code>@app.route("/messaging", methods=["GET", "POST"])
@login_required
def messaging():
    if request.method == "GET":

        clicked_user = request.args.get('user')
        messages = db.execute("SELECT * FROM messages WHERE (m_sending_user = :self_user AND m_receiving_user = :other_user) OR (m_sending_user = :other_user AND m_receiving_user = :self_user)",
                        self_user = session["user_id"],
                        other_user = clicked_user)

        return render_template("messaging.html", messages=messages, clicked_user=clicked_user)

    if request.method == "POST":

        receiving_user = request.form.get("recipient")

        db.execute("INSERT INTO messages (m_sending_user, m_receiving_user, message) VALUES (:m_sending_user, :m_receiving_user, :message)",
                        m_sending_user = session["user_id"],
                        m_receiving_user = receiving_user,
                        message = request.form.get("reply"))

        flash("Sent!")
        return render_template("messaging.html")
</code>```

答:
Why do you not simply have the post function also call the get function like so

```<code>def get_function(clicked_user):
    messages = db.execute("SELECT * FROM messages WHERE (m_sending_user = :self_user AND m_receiving_user = :other_user) OR (m_sending_user = :other_user AND m_receiving_user = :self_user)",
                  self_user = session["user_id"],
                  other_user = clicked_user)

    return render_template("messaging.html", messages=messages, clicked_user=clicked_user)

@app.route("/messaging", methods=["GET", "POST"])
@login_required
def messaging():
    if request.method == "GET":

        clicked_user = request.args.get('user')

        return get_function(clicked_user)

    if request.method == "POST":

        receiving_user = request.form.get("recipient")

        db.execute("INSERT INTO messages (m_sending_user, m_receiving_user, message) VALUES (:m_sending_user, :m_receiving_user, :message)",
                        m_sending_user = session["user_id"],
                        m_receiving_user = receiving_user,
                        message = request.form.get("reply"))

        flash("Sent!")
        return get_function(m_receiving_user)
</code>```

But of course with better named functions ;)

Body:
I'm trying to write a simple messaging function and, despite searching, having trouble coming up with a workable solution. On the get function, the code retrieves stored messages and passes this to be rendered.

The post function stores the message which all works fine, however I'm trying to redirect the user back to the original page they came from to display the new message, hence trying to pass the receiving user variable to the get function.

My code so far below. I'm new to flask so would appreciate any other pointers as well. Thanks in advance!

@app.route("/messaging", methods=["GET", "POST"])
@login_required
def messaging():
    if request.method == "GET":

        clicked_user = request.args.get('user')
        messages = db.execute("SELECT * FROM messages WHERE (m_sending_user = :self_user AND m_receiving_user = :other_user) OR (m_sending_user = :other_user AND m_receiving_user = :self_user)",
                        self_user = session["user_id"],
                        other_user = clicked_user)

        return render_template("messaging.html", messages=messages, clicked_user=clicked_user)

    if request.method == "POST":

        receiving_user = request.form.get("recipient")

        db.execute("INSERT INTO messages (m_sending_user, m_receiving_user, message) VALUES (:m_sending_user, :m_receiving_user, :message)",
                        m_sending_user = session["user_id"],
                        m_receiving_user = receiving_user,
                        message = request.form.get("reply"))

        flash("Sent!")
        return render_template("messaging.html")

Body:
Why do you not simply have the post function also call the get function like so

def get_function(clicked_user):
    messages = db.execute("SELECT * FROM messages WHERE (m_sending_user = :self_user AND m_receiving_user = :other_user) OR (m_sending_user = :other_user AND m_receiving_user = :self_user)",
                  self_user = session["user_id"],
                  other_user = clicked_user)

    return render_template("messaging.html", messages=messages, clicked_user=clicked_user)

@app.route("/messaging", methods=["GET", "POST"])
@login_required
def messaging():
    if request.method == "GET":

        clicked_user = request.args.get('user')

        return get_function(clicked_user)

    if request.method == "POST":

        receiving_user = request.form.get("recipient")

        db.execute("INSERT INTO messages (m_sending_user, m_receiving_user, message) VALUES (:m_sending_user, :m_receiving_user, :message)",
                        m_sending_user = session["user_id"],
                        m_receiving_user = receiving_user,
                        message = request.form.get("reply"))

        flash("Sent!")
        return get_function(m_receiving_user)

But of course with better named functions ;)


答: So, you're updating something in componentDidUpdate that is in the state, and updating the state triggers this, so it's in an infinite loop, could you explain what you're trying to do I could give a solution?</p>

Title: what happen with my componentDidUpdate in reactjs?


问:
getting a 403 error from youtube data API
I'm getting a 403 error from youtube data API.
Its confusing because I'm getting that my credinal key isn't enabled but in the developer console the key is enbaled, and I'm getting 100% errors.

答: My youtube project was corrupted, i deleted it and created a new one and it worked.</p>


问:
How can I redirect MVC5 RedirectResult () to a full page in Asp.net?
In my ASP.NET MVC5 page I have an individual login feature with timeout. This works fine, once the timeout has expired, the login page opens at the next action and then it goes on.
There is only one layout problem. If I click on a logged-out user in a PartialView, the login page is rendered in this PartialView and not on the whole page.
Code for authentication:

```<code>        public void OnAuthenticationChallenge(AuthenticationChallengeContext filterContext)
    {
        if (filterContext.Result == null || filterContext.Result is HttpUnauthorizedResult)
        {
            filterContext.HttpContext.Session["PlantId"] = filterContext.HttpContext.Request.QueryString["PlantId"];
            filterContext.HttpContext.Session["ShowOnlyEnabledRecipes"] = filterContext.HttpContext.Request.QueryString["ShowOnlyEnabledRecipes"];
             filterContext.Result = new RedirectResult("~/UserLogin/Login");
        }
    }
</code>```

And Controller:

```<code>    [HttpPost]
    public ActionResult Login(LoginModel loginModel)
    {
        Initialize();
         ...
        return View(loginModel);
            }
</code>```

How can I ensure that the login form always occupies an entire page? Also, if it is called by clicking on a PartialView?

答:
Do redirect in the PartialView(the controller for PartialView), the result only render in the area, if you want to direct to another page(url changed), you need to add below code in the controller. You will have advanced info from Ref link.

P.S. ActionFilter cannot return JavaScript, please put in the normal controller.

Ref: http://geekswithblogs.net/DougLampe/archive/2011/08/05/redirecting-from-a-partial-view-the-right-way-in-asp.net.aspx

```<code>string virtualPath = System.Web.HttpContext.Current.Request.Url.GetLeftPart(UriPartial.Authority) + HttpRuntime.AppDomainAppVirtualPath;
string returnUrl = virtualPath + "/UserLogin/Login";
return JavaScript( string .Format( "document.location = '{0}';" , returnUrl));
</code>```

Body:
In my ASP.NET MVC5 page I have an individual login feature with timeout. This works fine, once the timeout has expired, the login page opens at the next action and then it goes on.
There is only one layout problem. If I click on a logged-out user in a PartialView, the login page is rendered in this PartialView and not on the whole page.
Code for authentication:

        public void OnAuthenticationChallenge(AuthenticationChallengeContext filterContext)
    {
        if (filterContext.Result == null || filterContext.Result is HttpUnauthorizedResult)
        {
            filterContext.HttpContext.Session["PlantId"] = filterContext.HttpContext.Request.QueryString["PlantId"];
            filterContext.HttpContext.Session["ShowOnlyEnabledRecipes"] = filterContext.HttpContext.Request.QueryString["ShowOnlyEnabledRecipes"];
             filterContext.Result = new RedirectResult("~/UserLogin/Login");
        }
    }

And Controller:

    [HttpPost]
    public ActionResult Login(LoginModel loginModel)
    {
        Initialize();
         ...
        return View(loginModel);
            }

How can I ensure that the login form always occupies an entire page? Also, if it is called by clicking on a PartialView?

Body:
Do redirect in the PartialView(the controller for PartialView), the result only render in the area, if you want to direct to another page(url changed), you need to add below code in the controller. You will have advanced info from Ref link.

P.S. ActionFilter cannot return JavaScript, please put in the normal controller.

Ref: http://geekswithblogs.net/DougLampe/archive/2011/08/05/redirecting-from-a-partial-view-the-right-way-in-asp.net.aspx

string virtualPath = System.Web.HttpContext.Current.Request.Url.GetLeftPart(UriPartial.Authority) + HttpRuntime.AppDomainAppVirtualPath;
string returnUrl = virtualPath + "/UserLogin/Login";
return JavaScript( string .Format( "document.location = '{0}';" , returnUrl));


问:
onAppOpenAttribution not called for deep links with AppsFlyer
I have integrated the AppsFlyer SDK into my project. I have managed to get deep links working. Any links I make in OneLink will open the app as desired. However I have no way to access the link parameters. I have implemented all the following delegate methods like so:

```<code>func onAppOpenAttribution(_ attributionData: [AnyHashable : Any]!) {
    print("Test 1")
}

func onAppOpenAttributionFailure(_ error: Error!) {
    print("Test 2")
}

func onConversionDataReceived(_ installData: [AnyHashable : Any]!) {
    print("Test 3")
}

func onConversionDataRequestFailure(_ error: Error!) {
    print("Test 4")
}
</code>```

Not one of them is called when my app is open from a deep link. What am I missing here? In my URL that is configured in the control panel I have mycompany:// configured as the Mobile deeplink URL. Any pointers on this would be great. Thanks!

答:
According to the AppsFlyer document: initializing the SDK, you need to check the following conditions:

Invoke AppsFlyerTracker.shared.trackAppLaunch() when UIApplication.didBecomeActiveNotification posted or in the function applicationDidBecomeActive(_:).

Set AppsFlyerTracker.shared.isStopTracking = false

Pass userActivity to AppsFlyerManager.shared.continue(_) in application(_:continue:restorationHandler:) for universal link (http:// or https://).

Pass URL and options to AppsFlyerManager.shared.handleOpen(_:options:) in application(_:open:options:) for deep link (custom scheme).

Set tracker delegate to AppsFlyerTracker.shared.delegate.

After calling AppsFlyerTracker.shared.trackAppLaunch(), the callback function onAppOpenAttribution(_ attributionData:) of the delegate will pass the link information as well.

Body:
I have integrated the AppsFlyer SDK into my project. I have managed to get deep links working. Any links I make in OneLink will open the app as desired. However I have no way to access the link parameters. I have implemented all the following delegate methods like so:

func onAppOpenAttribution(_ attributionData: [AnyHashable : Any]!) {
    print("Test 1")
}

func onAppOpenAttributionFailure(_ error: Error!) {
    print("Test 2")
}

func onConversionDataReceived(_ installData: [AnyHashable : Any]!) {
    print("Test 3")
}

func onConversionDataRequestFailure(_ error: Error!) {
    print("Test 4")
}

Not one of them is called when my app is open from a deep link. What am I missing here? In my URL that is configured in the control panel I have mycompany:// configured as the Mobile deeplink URL. Any pointers on this would be great. Thanks!


问:
How to get the value of the $(this) selector in click or change even
I have already tried this :

```<code>" document.getElementById("ium_textbox")"
</code>```

but it just can find the first one ium_textbox.text

how can I find textbox text in the same
 :

答:
If you want to extract the second input text, then you need to use the class name

Javascript

```<code>var x = document.getElementsByClassName("ium_textbox");
</code>```

Jquery

If you want to extract the first input text, then you need to use the class name

```<code>var value1 = $(".ium_textbox").val();
   alert(value1);
</code>```

If you want to extract the first input text, then you need to use the ID name

```<code>var value2 = $("#ium_textbox").val();
   alert(value2);
</code>```

Body:
I have already tried this :

" document.getElementById("ium_textbox")"

but it just can find the first one ium_textbox.text

how can I find textbox text in the same
 :

Body:
If you want to extract the second input text, then you need to use the class name

Javascript

var x = document.getElementsByClassName("ium_textbox");

Jquery

If you want to extract the first input text, then you need to use the class name

var value1 = $(".ium_textbox").val();
   alert(value1);

If you want to extract the first input text, then you need to use the ID name

var value2 = $("#ium_textbox").val();
   alert(value2);


问:
How to navigate to secondary router outlet that sits in component that is displayed in primary router outlet?
So, after hours of searching I couldn't find a similar problem. The setup is as follows: one app module and one routing module. Component that is displayed in primary router outlet is user-component and primary router outlet is in app-component html file. I want to navigate to router outlet that sits in html of user-component. I only found nested routing and multi-outlet routing examples/solutions that navigate through app where all or both routers are in the same html file. Is this somehow possible?</p>

答:
If you want to achieve without named outlet :-

In your routing config what ever component you want to display inside router outlet inside user component should be as children routes under user component :- for eg:

```<code>   [
     {
       path: 'user',
       component: UserComponent,
       children: [
         {
            path: 'info',
            component: UserInfoComponent
         }
       ]
     }
   ]
</code>```

If you want to achieve it via named router-outlet
Give a name to router-outlet inside user component, lets say abc.

With routes of component which you want to show inside this outlet
Give outlet property as abc. while routing tell which auxiliary route to choose.

this.router.navigate(["user", { outlets: { abc: ["info"] } }]);

And your routing config will be :-

[
         {
           path: 'user',
           component: UserComponent,
           children: [
             {
                path: 'info',
                component: UserInfoComponent,
                outlet: "abc"
             }
           ]
         }
       ]

Body:
If you want to achieve without named outlet :-

In your routing config what ever component you want to display inside router outlet inside user component should be as children routes under user component :- for eg:

   [
     {
       path: 'user',
       component: UserComponent,
       children: [
         {
            path: 'info',
            component: UserInfoComponent
         }
       ]
     }
   ]

If you want to achieve it via named router-outlet
Give a name to router-outlet inside user component, lets say abc.

With routes of component which you want to show inside this outlet
Give outlet property as abc. while routing tell which auxiliary route to choose.

this.router.navigate(["user", { outlets: { abc: ["info"] } }]);

And your routing config will be :-

[
         {
           path: 'user',
           component: UserComponent,
           children: [
             {
                path: 'info',
                component: UserInfoComponent,
                outlet: "abc"
             }
           ]
         }
       ]


问:
English characters don't show up when entering text with Indic input method in Swing
I'm working on an application that accepts text in English and performs transliteration with a custom 3rd party API into an Indic language (one of several that are supported). The application is targeted at Windows XP/7 and Ubuntu.
We use a custom input method that loads the required Indic font, and uses it render text. Also, the user can correct the transliterated text by typing in English and pressing space (similar to how Google Transliterate works).

The problem is that with certain Indic fonts, typing in English shows up empty box characters (even though the actual characters typed are detected and transliterated accordingly).

I have used the ttf-indic-fonts-0.5.0 font pack that comes with Ubuntu, and was able to substitute some of them. For the others, if I copy the corresponding font from Windows (I'm developing this on Windows 7) then all problems are solved.

However, we cannot redistribute Windows fonts with our application and want an open alternative.

Other than trying to find a substitute font, is there anything else that we're doing wrong, or need to check, to make sure that English characters can be typed in a JTextField when an Indic font is being used?

As an example - from the Ubuntu package mentioned above, the lohit_pa.ttf font for Punjabi has this problem. If I copy the default Windows font for Punjabi (raavi.ttf) then it works fine.

答:
I found a solution to the problem. I installed the fonts on Windows (open the font, click install) and browsed the contents using Character Map. These fonts only have glyphs for the language in question, not English.
I used FontForge to merge the 2 fonts. (Fontforge's author doesn't provide binaries anymore - but if you have access to Ubuntu you can install it from the repository. No such luck if you only have Windows).
After this, I'm able to type in English again.</p>


问:
Rotating multi-dimensional array by 90 degrees clockwise
I've been able to work out the bulk of the problem. But my output keeps throwing an exception. I'm sure it's something minor, but I can't seem to figure out how to make this work right. I'm including the exception, the task as originally worded to me, along with my code so far:

Using formula array[j][n - 1 - i] I get the following exception:

Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index -1 out of bounds for length 4
at com.company.Main.main(Main.java:20)

If I use array[j][n - i] I get no exception, but it isn't the correct output order.

Been stuck on this for a week!

Given a rectangle array n×m in size. Rotate it by 90 degrees clockwise, by recording the result into the new array m×n in size.

Input data format:

Input the two numbers n and m, not exceeding 100, and then an array n×m in size.

Output data format:

Output the resulting array. Separate numbers by a single space in the output.

Sample Input 1:

```<code>3 4

11 12 13 14
21 22 23 24
31 32 33 34
</code>```

Sample Output 1:

```<code>31 21 11
32 22 12
33 23 13
34 24 14
</code>```

```<code>class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        int m = scanner.nextInt();
        int[][] array = new int[n][m];

        for (int i = 0; i < n; i++) {
            for (int j = 0; j < m; j++) {
                array[i][j] = scanner.nextInt();
            }
        }
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                System.out.print(array[j][n - 1 - i] + " ");
            }
            System.out.println("");
        }
    }
}
</code>```

答:
If you're only rotating it 90 degrees, you're just starting from the end of the row to the beginning while moving columns left and right. So your code should just be:

int n = 3;
int m = 4;

int[][] array = {
        {11, 12, 13, 14},
        {21, 22, 23, 24},
        {31, 32, 33, 34}};

for (int col = 0; col < m; col++) {
    for (int row = n - 1; row >= 0; row--) {
        System.out.print(array[row][col] + " ");
    }
    System.out.println("");
}
```

Body:
I've been able to work out the bulk of the problem. But my output keeps throwing an exception. I'm sure it's something minor, but I can't seem to figure out how to make this work right. I'm including the exception, the task as originally worded to me, along with my code so far:

Using formula array[j][n - 1 - i] I get the following exception:

Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index -1 out of bounds for length 4
at com.company.Main.main(Main.java:20)

If I use array[j][n - i] I get no exception, but it isn't the correct output order.

Been stuck on this for a week!

Given a rectangle array n×m in size. Rotate it by 90 degrees clockwise, by recording the result into the new array m×n in size.

Input data format:

Input the two numbers n and m, not exceeding 100, and then an array n×m in size.

Output data format:

Output the resulting array. Separate numbers by a single space in the output.

Sample Input 1:

3 4

11 12 13 14
21 22 23 24
31 32 33 34

Sample Output 1:

31 21 11
32 22 12
33 23 13
34 24 14

class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        int m = scanner.nextInt();
        int[][] array = new int[n][m];

        for (int i = 0; i < n; i++) {
            for (int j = 0; j < m; j++) {
                array[i][j] = scanner.nextInt();
            }
        }
        for (int i = 0; i < m; i++) {
            for (int j = 0; j < n; j++) {
                System.out.print(array[j][n - 1 - i] + " ");
            }
            System.out.println("");
        }
    }
}


问:
ValueError: Iterable over raw text documents expected, string object received. Predicting new test data with tfidf and selection feature
So i have build a model with sklearn Naive Bayes classifier.
I need to know how to predict a sentence with input

when i just hardcode the sentence its work fine, look like this

```<code>new_sentence = ['its so broken']
new_testdata_tfidf= tfidf.transform(new_sentence)
#transform it to matrix to see the score TFIDF on the training data
fit_feature_selection = selection.transform(new_testdata_tfidf)
#transform the new data to see if the feature remove or not, because after tfidf i use chi2 selection feature.
predicted = classifier.predict(feature_selection )
#then predict it. the classificaiton out, the class is -1 which is the correct answer
</code>```

i need to type the text data with hand as an input so I use like this

```<code>new_sentence = input[('')]
#i input the same sentence its so broken
new_testdata_tfidf= tfidf.transform(new_sentence)
#transform it to matrix to see the score TFIDF on the training data
fit_feature_selection = selection.transform(new_testdata_tfidf)
#transform the new data to see if the feature remove or not, because after tfidf i use chi2 selection feature.
predicted = classifier.predict(feature_selection )
</code>```

but it give me output

```<code>  File "C:\Users\Myfile\OneDrive\Desktop\model.py", line 170, in <module>
   new_testdata_tfidf= tfidf.transform(new_sentence)

  File "E:\anaconda3\lib\site-packages\sklearn\feature_extraction\text.py", line 1898, in transform
    X = super().transform(raw_documents)

  File "E:\anaconda3\lib\site-packages\sklearn\feature_extraction\text.py", line 1265, in transform
    "Iterable over raw text documents expected, "

ValueError: Iterable over raw text documents expected, string object received.
</code>```

How to resolve this?
any help really appreciated.

答:
If you are trying to pass the list of strings with new_sentence = input[('')]  in your code, then you might want to replace it with

```<code>new_sentence = [input()]
</code>```

Hope this helps.

Body:
So i have build a model with sklearn Naive Bayes classifier.
I need to know how to predict a sentence with input

when i just hardcode the sentence its work fine, look like this

new_sentence = ['its so broken']
new_testdata_tfidf= tfidf.transform(new_sentence)
#transform it to matrix to see the score TFIDF on the training data
fit_feature_selection = selection.transform(new_testdata_tfidf)
#transform the new data to see if the feature remove or not, because after tfidf i use chi2 selection feature.
predicted = classifier.predict(feature_selection )
#then predict it. the classificaiton out, the class is -1 which is the correct answer

i need to type the text data with hand as an input so I use like this

new_sentence = input[('')]
#i input the same sentence its so broken
new_testdata_tfidf= tfidf.transform(new_sentence)
#transform it to matrix to see the score TFIDF on the training data
fit_feature_selection = selection.transform(new_testdata_tfidf)
#transform the new data to see if the feature remove or not, because after tfidf i use chi2 selection feature.
predicted = classifier.predict(feature_selection )

but it give me output

  File "C:\Users\Myfile\OneDrive\Desktop\model.py", line 170, in <module>
   new_testdata_tfidf= tfidf.transform(new_sentence)

  File "E:\anaconda3\lib\site-packages\sklearn\feature_extraction\text.py", line 1898, in transform
    X = super().transform(raw_documents)

  File "E:\anaconda3\lib\site-packages\sklearn\feature_extraction\text.py", line 1265, in transform
    "Iterable over raw text documents expected, "

ValueError: Iterable over raw text documents expected, string object received.

How to resolve this?
any help really appreciated.

Body:
If you are trying to pass the list of strings with new_sentence = input[('')]  in your code, then you might want to replace it with

new_sentence = [input()]

Hope this helps.


问:
cant access string methods in dbplyr
I am trying to use str_detect, str_replace, str_replace_all methods in dbplyr with oracle as the beckend database but cant seem to access this methods.

here is the error:

db_tbl %>% mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>% show_query()
```

<pre class="lang-r prettyprint-override"><code>Error: str_detect() is not available in this SQL variant
</code>```

I have reinstalled all the packages but still no use.
However, I can see that it was implemented in dbplyr 1.2.0 see here?

tried with grepl which translates to this:

```<code>db_tbl %>% mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>% show_query()
</code>```

<SQL>
Named arguments ignored for SQL greplSELECT grepl("COMMENTS", '[^[:alnum:]]' AS "pattern") AS "COMMENTS_NEW"
FROM ("schema".table)
```

<p>also returns the error. here is the traceback:</p>

<pre class="lang-r prettyprint-override"><code>20.
stop(structure(list(message = "<SQL> 'SELECT * FROM (SELECT \"COMMENTS\", \"TYPE_28\", grepl(\"COMMENTS\", '[^[:alnum:]]' AS \"pattern\") AS \"COMMENTS_NEW\"\nFROM (\"schema\".table) ) \"zzz3\" WHERE ROWNUM <= 6.0'\n nanodbc/nanodbc.cpp:1587: HY000: [Oracle][ODBC][Ora]ORA-00907: missing right parenthesis\n ", call = NULL, cppstack = NULL), class = c("odbc::odbc_error", "C++Error", "error", "condition")))
19.
new_result(connection@ptr, statement)
18.
OdbcResult(connection = conn, statement = statement)
17.
dbSendQuery(con, sql)
16.
dbSendQuery(con, sql)
15.
db_collect.DBIConnection(x$src$con, sql, n = n, warn_incomplete = warn_incomplete)
14.
db_collect(x$src$con, sql, n = n, warn_incomplete = warn_incomplete)
13.
collect.tbl_sql(x, n = n)
12.
collect(x, n = n)
11.
as.data.frame(collect(x, n = n))
10.
as.data.frame.tbl_sql(head(x, n + 1))
9.
as.data.frame(head(x, n + 1))
8.
trunc_mat(x, n = n, width = width, n_extra = n_extra)
7.
format.tbl(x, ..., n = n, width = width, n_extra = n_extra)
6.
format(x, ..., n = n, width = width, n_extra = n_extra)
5.
paste0(..., "\n")
4.
cat(paste0(..., "\n"), sep = "")
3.
cat_line(format(x, ..., n = n, width = width, n_extra = n_extra))
2.
print.tbl_sql(x)
1.
function (x, ...) UseMethod("print")(x)

</code>```

heres my session:

R version 3.5.0 (2018-04-23)
Platform: x86_64-w64-mingw32/x64 (64-bit)
Running under: Windows >= 8 x64 (build 9200)

Matrix products: default

locale:
[1] LC_COLLATE=English_United Kingdom.1252  LC_CTYPE=English_United Kingdom.1252    LC_MONETARY=English_United Kingdom.1252
[4] LC_NUMERIC=C                            LC_TIME=English_United Kingdom.1252

attached base packages:
[1] stats     graphics  grDevices utils     datasets  methods   base

other attached packages:
 [1] dbplot_0.3.2           pool_0.1.4.2           dbplyr_1.4.2           DBI_1.0.0              odbc_1.1.6             data.table_1.11.8
 [7] qdap_2.3.0             RColorBrewer_1.1-2     qdapTools_1.3.3        qdapRegex_0.7.2        qdapDictionaries_1.0.7 textclean_0.9.3
[13] drlib_0.1.0            lubridate_1.7.4        ggrepel_0.8.0          fpp2_2.3               expsmooth_2.3          fma_2.3
[19] forecast_8.5           recipes_0.1.5          textSummary_0.1.0      scales_1.0.0           janitor_1.1.1          forcats_0.3.0
[25] stringr_1.4.0          dplyr_0.8.1            purrr_0.2.5            readr_1.2.1            tidyr_0.8.2            tibble_2.1.1
[31] ggplot2_3.2.0          tidyverse_1.2.1

loaded via a namespace (and not attached):
  [1] openNLPdata_1.5.3-4 colorspace_1.4-1    class_7.3-14        rprojroot_1.3-2     fs_1.2.6            base64enc_0.1-3
  [7] rstudioapi_0.8      remotes_2.0.2       bit64_0.9-7         prodlim_2018.04.18  fansi_0.4.0         xml2_1.2.0
 [13] splines_3.5.0       knitr_1.20          pkgload_1.0.2       jsonlite_1.6        venneuler_1.1-0     rJava_0.9-10
 [19] broom_0.5.1         compiler_3.5.0      httr_1.3.1          backports_1.1.2     assertthat_0.2.1    Matrix_1.2-14
 [25] lazyeval_0.2.2      cli_1.1.0           later_0.8.0         prettyunits_1.0.2   tools_3.5.0         igraph_1.2.2
 [31] NLP_0.2-0           gtable_0.3.0        glue_1.3.1          reshape2_1.4.3      Rcpp_1.0.1          slam_0.1-43
 [37] cellranger_1.1.0    fracdiff_1.4-2      urca_1.3-0          gdata_2.18.0        nlme_3.1-137        lmtest_0.9-36
 [43] timeDate_3043.102   gower_0.1.2         gender_0.5.2        ps_1.2.1            xlsxjars_0.6.1      testthat_2.0.1
 [49] rvest_0.3.2         devtools_2.0.1      gtools_3.8.1        XML_3.98-1.16       xlsx_0.6.1          MASS_7.3-49
 [55] zoo_1.8-5           ipred_0.9-8         hms_0.4.2           parallel_3.5.0      yaml_2.2.0          quantmod_0.4-14
 [61] curl_3.3            memoise_1.1.0       gridExtra_2.3       rpart_4.1-13        stringi_1.4.3       desc_1.2.0
 [67] tseries_0.10-46     plotrix_3.7-4       TTR_0.23-4          pkgbuild_1.0.2      openNLP_0.2-6       lava_1.6.4
 [73] chron_2.3-53        rlang_0.4.0         pkgconfig_2.0.2     bitops_1.0-6        lattice_0.20-35     processx_3.2.0
 [79] bit_1.1-14          tidyselect_0.2.5    plyr_1.8.4          magrittr_1.5        R6_2.4.0            generics_0.0.2
 [85] pillar_1.3.1        haven_2.0.0         withr_2.1.2         xts_0.11-2          survival_2.41-3     RCurl_1.95-4.11
 [91] nnet_7.3-12         modelr_0.1.2        crayon_1.3.4        utf8_1.1.4          wordcloud_2.6       usethis_1.4.0
 [97] grid_3.5.0          readxl_1.1.0        callr_3.0.0         blob_1.1.1          reports_0.1.4       digest_0.6.18
[103] tm_0.7-5            munsell_0.5.0       sessioninfo_1.1.1   quadprog_1.5-5
```

答:
This is not really an answer, but, instead, just a simple workaround.

The problem is dbplyr:: cannot manage to create an adequate SQL clause (SQL has no functions with names str_detect or grepl), so it throws the towel (and an error).

In both the expressions, you get error because dbplyr cannot translate neitherstringr::str_detect()norbase::grepl()to a valid SQL expression.
One way to get almost what you want is tocollect()before youfilter()`:

```<code>db_tbl %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>%
  show_query()
db_tbl %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>%
  collect()
db_tbl %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>%
  show_query()
db_tbl %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>%
  collect()
</code>```

However, if you place collect() before...

```<code>db_tbl %>%
  collect() %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", ""))
db_tbl %>%
  collect() %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]'))
</code>```

your remote tables become local tables, on which you can apply str_detect() peacefully.

As a side comment, show_query() ceases to be meaningful for obvious reasons.

Title: cant access string methods in dbplyr

Body:
I am trying to use str_detect, str_replace, str_replace_all methods in dbplyr with oracle as the beckend database but cant seem to access this methods.

here is the error:

db_tbl %>% mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>% show_query()

Error: str_detect() is not available in this SQL variant

I have reinstalled all the packages but still no use.
However, I can see that it was implemented in dbplyr 1.2.0 see here?

tried with grepl which translates to this:

db_tbl %>% mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>% show_query()

<SQL>
Named arguments ignored for SQL greplSELECT grepl("COMMENTS", '[^[:alnum:]]' AS "pattern") AS "COMMENTS_NEW"
FROM ("schema".table)

also returns the error. here is the traceback:

20.
stop(structure(list(message = "<SQL> 'SELECT * FROM (SELECT \"COMMENTS\", \"TYPE_28\", grepl(\"COMMENTS\", '[^[:alnum:]]' AS \"pattern\") AS \"COMMENTS_NEW\"\nFROM (\"schema\".table) ) \"zzz3\" WHERE ROWNUM <= 6.0'\n nanodbc/nanodbc.cpp:1587: HY000: [Oracle][ODBC][Ora]ORA-00907: missing right parenthesis\n ", call = NULL, cppstack = NULL), class = c("odbc::odbc_error", "C++Error", "error", "condition")))
19.
new_result(connection@ptr, statement)
18.
OdbcResult(connection = conn, statement = statement)
17.
dbSendQuery(con, sql)
16.
dbSendQuery(con, sql)
15.
db_collect.DBIConnection(x$src$con, sql, n = n, warn_incomplete = warn_incomplete)
14.
db_collect(x$src$con, sql, n = n, warn_incomplete = warn_incomplete)
13.
collect.tbl_sql(x, n = n)
12.
collect(x, n = n)
11.
as.data.frame(collect(x, n = n))
10.
as.data.frame.tbl_sql(head(x, n + 1))
9.
as.data.frame(head(x, n + 1))
8.
trunc_mat(x, n = n, width = width, n_extra = n_extra)
7.
format.tbl(x, ..., n = n, width = width, n_extra = n_extra)
6.
format(x, ..., n = n, width = width, n_extra = n_extra)
5.
paste0(..., "\n")
4.
cat(paste0(..., "\n"), sep = "")
3.
cat_line(format(x, ..., n = n, width = width, n_extra = n_extra))
2.
print.tbl_sql(x)
1.
function (x, ...) UseMethod("print")(x)

heres my session:

R version 3.5.0 (2018-04-23)
Platform: x86_64-w64-mingw32/x64 (64-bit)
Running under: Windows >= 8 x64 (build 9200)

Matrix products: default

locale:
[1] LC_COLLATE=English_United Kingdom.1252  LC_CTYPE=English_United Kingdom.1252    LC_MONETARY=English_United Kingdom.1252
[4] LC_NUMERIC=C                            LC_TIME=English_United Kingdom.1252

attached base packages:
[1] stats     graphics  grDevices utils     datasets  methods   base

other attached packages:
 [1] dbplot_0.3.2           pool_0.1.4.2           dbplyr_1.4.2           DBI_1.0.0              odbc_1.1.6             data.table_1.11.8
 [7] qdap_2.3.0             RColorBrewer_1.1-2     qdapTools_1.3.3        qdapRegex_0.7.2        qdapDictionaries_1.0.7 textclean_0.9.3
[13] drlib_0.1.0            lubridate_1.7.4        ggrepel_0.8.0          fpp2_2.3               expsmooth_2.3          fma_2.3
[19] forecast_8.5           recipes_0.1.5          textSummary_0.1.0      scales_1.0.0           janitor_1.1.1          forcats_0.3.0
[25] stringr_1.4.0          dplyr_0.8.1            purrr_0.2.5            readr_1.2.1            tidyr_0.8.2            tibble_2.1.1
[31] ggplot2_3.2.0          tidyverse_1.2.1

loaded via a namespace (and not attached):
  [1] openNLPdata_1.5.3-4 colorspace_1.4-1    class_7.3-14        rprojroot_1.3-2     fs_1.2.6            base64enc_0.1-3
  [7] rstudioapi_0.8      remotes_2.0.2       bit64_0.9-7         prodlim_2018.04.18  fansi_0.4.0         xml2_1.2.0
 [13] splines_3.5.0       knitr_1.20          pkgload_1.0.2       jsonlite_1.6        venneuler_1.1-0     rJava_0.9-10
 [19] broom_0.5.1         compiler_3.5.0      httr_1.3.1          backports_1.1.2     assertthat_0.2.1    Matrix_1.2-14
 [25] lazyeval_0.2.2      cli_1.1.0           later_0.8.0         prettyunits_1.0.2   tools_3.5.0         igraph_1.2.2
 [31] NLP_0.2-0           gtable_0.3.0        glue_1.3.1          reshape2_1.4.3      Rcpp_1.0.1          slam_0.1-43
 [37] cellranger_1.1.0    fracdiff_1.4-2      urca_1.3-0          gdata_2.18.0        nlme_3.1-137        lmtest_0.9-36
 [43] timeDate_3043.102   gower_0.1.2         gender_0.5.2        ps_1.2.1            xlsxjars_0.6.1      testthat_2.0.1
 [49] rvest_0.3.2         devtools_2.0.1      gtools_3.8.1        XML_3.98-1.16       xlsx_0.6.1          MASS_7.3-49
 [55] zoo_1.8-5           ipred_0.9-8         hms_0.4.2           parallel_3.5.0      yaml_2.2.0          quantmod_0.4-14
 [61] curl_3.3            memoise_1.1.0       gridExtra_2.3       rpart_4.1-13        stringi_1.4.3       desc_1.2.0
 [67] tseries_0.10-46     plotrix_3.7-4       TTR_0.23-4          pkgbuild_1.0.2      openNLP_0.2-6       lava_1.6.4
 [73] chron_2.3-53        rlang_0.4.0         pkgconfig_2.0.2     bitops_1.0-6        lattice_0.20-35     processx_3.2.0
 [79] bit_1.1-14          tidyselect_0.2.5    plyr_1.8.4          magrittr_1.5        R6_2.4.0            generics_0.0.2
 [85] pillar_1.3.1        haven_2.0.0         withr_2.1.2         xts_0.11-2          survival_2.41-3     RCurl_1.95-4.11
 [91] nnet_7.3-12         modelr_0.1.2        crayon_1.3.4        utf8_1.1.4          wordcloud_2.6       usethis_1.4.0
 [97] grid_3.5.0          readxl_1.1.0        callr_3.0.0         blob_1.1.1          reports_0.1.4       digest_0.6.18
[103] tm_0.7-5            munsell_0.5.0       sessioninfo_1.1.1   quadprog_1.5-5

Body:
This is not really an answer, but, instead, just a simple workaround.

The problem is dbplyr:: cannot manage to create an adequate SQL clause (SQL has no functions with names str_detect or grepl), so it throws the towel (and an error).

In both the expressions, you get error because dbplyr cannot translate neitherstringr::str_detect()norbase::grepl()to a valid SQL expression.
One way to get almost what you want is tocollect()before youfilter()`:

db_tbl %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>%
  show_query()
db_tbl %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", "")) %>%
  collect()
db_tbl %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>%
  show_query()
db_tbl %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]')) %>%
  collect()

However, if you place collect() before...

db_tbl %>%
  collect() %>%
  mutate(COMMENTS_NEW = str_detect(COMMENTS,"[^[:alnum:]///' ]", ""))
db_tbl %>%
  collect() %>%
  mutate(COMMENTS_NEW = grepl(COMMENTS,pattern = '[^[:alnum:]]'))

your remote tables become local tables, on which you can apply str_detect() peacefully.

As a side comment, show_query() ceases to be meaningful for obvious reasons.


问:
Exporting a Dynamoose Typescript model

The dynamoose library provides the following signature for constructing a model:

```<code>    model: {
        <T extends Document>(name: string, schema?: SchemaDefinition | Schema, options?: Partial<import("./Model").ModelOptions>): T & Model<T> & ModelDocumentConstructor<T>;
        defaults: any;
    };
</code>```

Consumption in a TypeScript file is being done as follows:

import * as dynamoose from 'dynamoose';
...
const ExampleRepository = dynamoose.model(
  schemaName,
  ExampleSchema,
);

export default ExampleRepository;
```

<ol start="3">
<li>Compilation produces the error:</li>
</ol>

```Exported variable 'ExampleRepository' has or is using name 'ModelDocumentConstructor' from external module ".../node_modules/dynamoose/dist/index" but cannot be named.
```

Other answers to similar questions on SO would suggest that the ModelDocumentConstructor should be imported. TS4023: Exported Variable <x> has or is using name <y> from external module but cannot be named

However the interface itself is not exported, so cannot be imported.

答:
From document, it says typescript support is in beta, but npm install --save "dynamoose@beta" does not work.

Is the latest release support typescript already, or very limted.

Title: Exporting a Dynamoose Typescript model

Body:
The dynamoose library provides the following signature for constructing a model:

    model: {
        <T extends Document>(name: string, schema?: SchemaDefinition | Schema, options?: Partial<import("./Model").ModelOptions>): T & Model<T> & ModelDocumentConstructor<T>;
        defaults: any;
    };

Consumption in a TypeScript file is being done as follows:

import * as dynamoose from 'dynamoose';
...
const ExampleRepository = dynamoose.model(
  schemaName,
  ExampleSchema,
);

export default ExampleRepository;

Compilation produces the error:

Exported variable 'ExampleRepository' has or is using name 'ModelDocumentConstructor' from external module ".../node_modules/dynamoose/dist/index" but cannot be named.

Other answers to similar questions on SO would suggest that the ModelDocumentConstructor should be imported. TS4023: Exported Variable <x> has or is using name <y> from external module but cannot be named

However the interface itself is not exported, so cannot be imported.


问:
How can I get the text and its format from clipboard at the same time?

This is the text I want to copy on a page in the browser. I tried to use Clipboard.GetText(TextDataFormat.Html) to get the HTML in order to get the text and keep the format at the same time, but the InnerText turned to 简述?Func&amplt;T&ampgt;与?Action&amplt;T&ampgt;的区别. I can replace the escape characters by the characters they represent, but I don't know what original character the '?' was because I'm going to deal with huge information by code and it's meaningless if I have to check every sentence.

I also try this

string text = Clipboard.GetText(TextDataFormat.Html);
byte[] data = Encoding.Default.GetBytes(text);
text = Encoding.UTF8.GetString(data);
```

came out the same result.

And GetClipboardData(uint uFormat) in 'user32.dll' which not gonna help.

I actually could get the correct text 简述 Func<T>与 Action<T>的区别 by using Clipboard.GetText(TextDataFormat.UnicodeText), but it will lose the style.

There has to be a way I can get the text and the format at the same time because the docx or some other software can display the text in the correct format when you paste on it.

答: The text you are seeing is the actual string as it is in the web page before the browser interprets it. To convert those special sequences like &amplt;, use HtmlDecode. See https://learn.microsoft.com/en-us/dotnet/api/system.web.httputility.htmldecode?view=netcore-3.1

Body:
This is the text I want to copy on a page in the browser. I tried to use Clipboard.GetText(TextDataFormat.Html) to get the HTML in order to get the text and keep the format at the same time, but the InnerText turned to 简述?Func&amplt;T&ampgt;与?Action&amplt;T&ampgt;的区别. I can replace the escape characters by the characters they represent, but I don't know what original character the '?' was because I'm going to deal with huge information by code and it's meaningless if I have to check every sentence.

I also try this

string text = Clipboard.GetText(TextDataFormat.Html);
byte[] data = Encoding.Default.GetBytes(text);
text = Encoding.UTF8.GetString(data);

came out the same result.

And GetClipboardData(uint uFormat) in 'user32.dll' which not gonna help.

I actually could get the correct text 简述 Func<T>与 Action<T>的区别 by using Clipboard.GetText(TextDataFormat.UnicodeText), but it will lose the style.

There has to be a way I can get the text and the format at the same time because the docx or some other software can display the text in the correct format when you paste on it.