问:
How to convert HTML to PDF with python3
How to convert HTML to PDF with python3? i write some code about webView with pyqt5,and i want to convert the html in the webView  to pdf,what should i do?

i have tried to use the html2pdf,but it seem to only support python2.x
and i have tried to install the wkhtmltox-0.12.2.2_msvc2013-win64.exe and pdfkit,and then use the example code.

```<code>import pdfkit

pdfkit.from_url('http://google.com', 'out.pdf')
pdfkit.from_file('test.html', 'out.pdf')
pdfkit.from_string('Hello!', 'out.pdf')
</code>```

but i also failed.and the error is following.

```<code>Traceback (most recent call last):
File "E:\Python34\lib\site-packages\pdfkit\configuration.py", line 21,  in __init__
with open(self.wkhtmltopdf) as f:
FileNotFoundError: [Errno 2] No such file or directory: b''

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
  pdfkit.from_url('http://google.com', 'out.pdf')
File "E:\Python34\lib\site-packages\pdfkit\api.py", line 22, in from_url
configuration=configuration)
File "E:\Python34\lib\site-packages\pdfkit\pdfkit.py", line 38, in __init__
self.configuration = (Configuration() if configuration is None
File "E:\Python34\lib\site-packages\pdfkit\configuration.py", line 27, in __init__
'https://github.com/JazzCore/python-pdfkit/wiki/Installing-wkhtmltopdf' % self.wkhtmltopdf)
OSError: No wkhtmltopdf executable found: "b''"
If this file exists please check that this process can read it.   Otherwise please install wkhtmltopdf - https://github.com/JazzCore/python-pdfkit/wiki/Installing-wkhtmltopdf
</code>```

but i also failed.so what should i do?  My system is window7 x64 ,python's version is 3.4

答: 'set path' probably means add **.exe to the system environment variable $Path$. For example, add D:\Program Files\wkhtmltopdf\bin to $Path$.

Title: How to convert HTML to PDF with python3

Body:
How to convert HTML to PDF with python3? i write some code about webView with pyqt5,and i want to convert the html in the webView  to pdf,what should i do?

i have tried to use the html2pdf,but it seem to only support python2.x
and i have tried to install the wkhtmltox-0.12.2.2_msvc2013-win64.exe and pdfkit,and then use the example code.

import pdfkit

pdfkit.from_url('http://google.com', 'out.pdf')
pdfkit.from_file('test.html', 'out.pdf')
pdfkit.from_string('Hello!', 'out.pdf')

but i also failed.and the error is following.

Traceback (most recent call last):
File "E:\Python34\lib\site-packages\pdfkit\configuration.py", line 21,  in __init__
with open(self.wkhtmltopdf) as f:
FileNotFoundError: [Errno 2] No such file or directory: b''

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
  pdfkit.from_url('http://google.com', 'out.pdf')
File "E:\Python34\lib\site-packages\pdfkit\api.py", line 22, in from_url
configuration=configuration)
File "E:\Python34\lib\site-packages\pdfkit\pdfkit.py", line 38, in __init__
self.configuration = (Configuration() if configuration is None
File "E:\Python34\lib\site-packages\pdfkit\configuration.py", line 27, in __init__
'https://github.com/JazzCore/python-pdfkit/wiki/Installing-wkhtmltopdf' % self.wkhtmltopdf)
OSError: No wkhtmltopdf executable found: "b''"
If this file exists please check that this process can read it.   Otherwise please install wkhtmltopdf - https://github.com/JazzCore/python-pdfkit/wiki/Installing-wkhtmltopdf

but i also failed.so what should i do?  My system is window7 x64 ,python's version is 3.4


来源: stackexchange

问:
Loop - Accept multiple times input from a single textbox name in PHP
(this might get confusing) i have 2 textboxes which would accept color and amount from a user ten times:

```<code><form action="" method="POST">
  <i> color </i><input type="text" name="text[]">
  <i> color amount </i> <input type="number" name="num[]">
  <input type="submit" value="Go">
</form>
</code>```

Now what i want to happen is that instead of declaring ten text boxes for color and amount i would just want to loop it so that after the first color and amount had been sent it would again ask for 9 times without displaying 10 textboxes for each name. Is there a way in php to loop it?

Thanks.
Regars,
Russel

答:
@russel
try this. This one is in pure php.</p>

```<code><html>
<head>
    <title></title>
</head>
<body>
    <?php
    session_start();

    if(!isset($_POST['submit']))
    {

        $_SESSION['count']=0;

    }
    ?>
    <form action="" method="POST">
  <i> color </i><input type="text" name="text">
  <i> color amount </i> <input type="number" name="num">
  <input type="submit" value="Go" name="submit">
</form>

<?php
    if(isset($_POST['submit']))
    {
        echo $_POST['text'];
        echo "<br>";
        echo $_POST['num'];
        echo "<br>";
        $count=$_SESSION['count']++;
        if($count==9)
        {
            echo "you have received 10 values";
            echo "<br>";
            echo "press ok to get again";
            ?>
            <form method="post">
                <input type="submit" name="ok" value="ok">
            </form>
            <?php
            if(isset($_POST['ok']))
            {
            header("Refresh:0");
            }
        }
    }
    ?>
</body>
</html>
</code>```

ContentLicense: CC BY-SA 3.0

Body:
(this might get confusing) i have 2 textboxes which would accept color and amount from a user ten times:

<form action="" method="POST">
   color <input type="text" name="text[]">
   color amount  <input type="number" name="num[]">
  <input type="submit" value="Go">
</form>

Now what i want to happen is that instead of declaring ten text boxes for color and amount i would just want to loop it so that after the first color and amount had been sent it would again ask for 9 times without displaying 10 textboxes for each name. Is there a way in php to loop it?

Thanks.
Regars,
Russel

Body:
@russel
try this. This one is in pure php.

<html>
<head>
    <title></title>
</head>
<body>
    <?php
    session_start();

    if(!isset($_POST['submit']))
    {

        $_SESSION['count']=0;

    }
    ?>
    <form action="" method="POST">
  <i> color </i><input type="text" name="text">
  <i> color amount </i> <input type="number" name="num">
  <input type="submit" value="Go" name="submit">
</form>

<?php
    if(isset($_POST['submit']))
    {
        echo $_POST['text'];
        echo "<br>";
        echo $_POST['num'];
        echo "<br>";
        $count=$_SESSION['count']++;
        if($count==9)
        {
            echo "you have received 10 values";
            echo "<br>";
            echo "press ok to get again";
            ?>
            <form method="post">
                <input type="submit" name="ok" value="ok">
            </form>
            <?php
            if(isset($_POST['ok']))
            {
            header("Refresh:0");
            }
        }
    }
    ?>
</body>
</html>


问:
Using SWT under OSX
I try to test a simple java application with SWT under Mac OS X. I can compile the source file without any problems but if I start the program then the following exception occurs:

```<code>java.lang.UnsatisfiedLinkError: Cannot load 32-bit SWT libraries on 64-bit JVM
</code>```

The command to compile is: "javac -classpath .:swt.jar SWTHello.java"
The command to run is: "java -d64 -XstartOnFirstThread -cp .:swt.jar SWTHello"

For the SWT library there's only one current osx version on the website so I guess I couldn't download a wrong jar.

Thanks in advance for your help!

答:
Change the SWT jar in your project classpath, You are using a 32 bits cocoa, use the 64 bits:

http://mvnrepository.com/artifact/org.eclipse.platform/org.eclipse.swt.cocoa.macosx.x86_64

Title: Using SWT under OSX

Body:
I try to test a simple java application with SWT under Mac OS X. I can compile the source file without any problems but if I start the program then the following exception occurs:

java.lang.UnsatisfiedLinkError: Cannot load 32-bit SWT libraries on 64-bit JVM

The command to compile is: "javac -classpath .:swt.jar SWTHello.java"
The command to run is: "java -d64 -XstartOnFirstThread -cp .:swt.jar SWTHello"

For the SWT library there's only one current osx version on the website so I guess I couldn't download a wrong jar.

Thanks in advance for your help!


问:
What is wrong with this IF statement in rails?
I am trying to only show comments if there are any comments as when there are no comments the for loop shows this (the hash table at the bottom)

The if statement in my code is

```<code><h2>Comments</h2>
<% if @article.comments.any? %>

<%= @article.comments.each do |comment| %>

<p>
  <strong>Commenter:</strong>
  <%= comment.commenter %>
 </p>

 <p>
  <strong>Comment:</strong>
  <%= comment.comment %>
 </p>

 <% end %>
<% end %>
</code>```

What is wrong with my code that it still enters the for loop even when there are no comments?

答:
In erb templates,

<%   %> used  to execute ruby code (loops, calculations, variable assignments, etc)

<%=  %> used to print something into resulting HTML template

<%#  %> used for comments (not printed on generated HTML) on erb templates

So, your erb file should look like this:

```<code><h2>Comments</h2>
<% if @article.comments.any? %>
  <% @article.comments.each do |comment| %>
    <p>
      <strong>Commenter:</strong>
      <%= comment.commenter %>
    </p>

    <p>
      <strong>Comment:</strong>
      <%= comment.comment %>
    </p>
  <% end %>
<% end %>
</code>```

Body:
I am trying to only show comments if there are any comments as when there are no comments the for loop shows this (the hash table at the bottom)

The if statement in my code is

Comments

<% if @article.comments.any? %>

<%= @article.comments.each do |comment| %>

  Commenter:
  <%= comment.commenter %>

  Comment:
  <%= comment.comment %>

 <% end %>
<% end %>

What is wrong with my code that it still enters the for loop even when there are no comments?

Body:
In erb templates,

<%   %> used  to execute ruby code (loops, calculations, variable assignments, etc)

<%=  %> used to print something into resulting HTML template

<%#  %> used for comments (not printed on generated HTML) on erb templates

So, your erb file should look like this:

<h2>Comments</h2>
<% if @article.comments.any? %>
  <% @article.comments.each do |comment| %>
    <p>
      <strong>Commenter:</strong>
      <%= comment.commenter %>
    </p>

    <p>
      <strong>Comment:</strong>
      <%= comment.comment %>
    </p>
  <% end %>
<% end %>


问:
hiding xml from public direct access
so my question is how do i prevent public access to an xml file on my server..

i have a website which allows users to listen to music online but you can't download... the music is in a flash player reading off an xml file..

the playlist for example will be named playlist.xml

how do i prevent the public to directly accessing the xml file if found via "view source" ?

is this possible if so how do i change settings?

答:
You can't. The Flash client, running on the user's computer, has to be able to access the file. If it can access the file, then anything else running on the user's computer can too.

You could try adding in extra required HTTP headers (by editing the Flash player) but that is not difficult to bypass.

ContentLicense: CC BY-SA 2.5

Title: hiding xml from public direct access


问:
RNN Training Loss Goes Down Then Acts Erratically
I've been trying to create a vanilla 3 layer RNN in Python 3.6, but whenever I train it the training loss decreases for the first X amount of training iterations then goes up and down sporadically and I can't identify the problem. I don't want to use Tensorflow or Keras or any deep learning framework for now because I'm trying to get a better understanding of how these NNs work.

I'm pretty sure my problem lies either in the way I added matrices together in my forward prop function, or in my get error and weight update part of my backprop function so I will post them both below.

Sorry if my code is a bit messy but here is my function that forward props through my neural network.

```<code>def RNN_forward(self, A):

    #input layer
    self.A = A

    #self.AB is a-b weight matrix
    self.B1 = np.dot(self.A, self.AB)

    #self.B_t is self.B (layer 2) from the previous timestep
    self.B_t1 = np.dot(self.B_t, self.B_RNN)

    #combining matrices
    self.B = self.sigmoid((self.B1) + (self.B_t1))
    self.C1 = np.dot(self.B, self.BC)

    #output layer
    self.C = self.sigmoid(self.C1)
    return self.C
</code>```

My backprop and update weight matrix functions are mushed into one function, sorry everything is so messy

```<code>def RNN_backprop(self, C_real):

    #did this so I could transpose a 1D matrix
    BT = self.B[np.newaxis]

    #get error of BC weight matrix
    delta3 = np.multiply(-(C_real-self.C), self.sigmoidPrime(self.C1))
    BCp = np.dot(BT.T, delta3)
    BCpT = BCp[np.newaxis]

    #get error of AB weight matrix
    delta2 = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B1)
    AT, d2 = self.A[np.newaxis], delta2[np.newaxis]
    ABp = np.dot(AT.T, d2)

    #get error of weight matrix linked to previous time step
    delta2t = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B_t1)
    B_RNNT, d2t = self.B_t[np.newaxis], delta2t[np.newaxis]
    B_RNNp = np.dot(B_RNNT.T, d2t)

    #training speed
    weight_multiplier = 10

    #update weight matricies
    self.BC = self.BC - BCpT.T*weight_multiplier
    self.AB = self.AB - ABp*weight_multiplier
    self.B_RNN = self.B_RNN - B_RNNp*weight_multiplier

    #store layer 2 to be used in next timestep
    self.B_t = self.B
</code>```

I am happy to post the entire code or any other bits that anyone might need to help diagnose my problem.

Thanks in advance for any advice or potential solutions you might have!

Edit:  Here is the entire code: it is really poorly commented so it's going to be difficult to read it but its all here. Some lines are commented out just because I wasn't sure if I was going to try and use them or not.

import numpy as np

class NN(object):

```<code>def __init__(self):
    self.A_size = 4
    self.B_size = 6
    self.C_size = 1

def init_weights(self):
    self.AB = np.random.randn(self.A_size, self.B_size)
    self.BC = np.random.randn(self.B_size, self.C_size)
    self.B_t = [0]
    self.B_RNN = np.random.randn(self.B_size, self.B_size)

def sigmoid(self, X1):
    return 1/(1+np.exp(-X1))

def sigmoidPrime(self,X1):
    return np.exp(-X1)/((1+np.exp(-X1))**2)

def print_status(self, NN_type):
    print("---------Status---------")
    print("A: ", self.A)
    print("AB: ", self.AB)
    print("B: ", self.B)
    print("BC: ", self.BC)
    print("C: ", self.C)
    if NN_type == "RNN":
        print("Previous B: ", self.B_t)
    if NN_type == "LSTM":
        pass
    #print("Error: ", self.cost)
    print("---------Done---------")

def RNN_forward(self, A):
    self.A = A
    self.B1 = np.dot(self.A, self.AB)
    if len(self.B_t) > 2:
        self.B_t1 = np.dot(self.B_t, self.B_RNN)
        self.B = self.sigmoid((self.B1) + (self.B_t1))
        #self.B = self.sigmoid(np.tanh(self.B1) + np.tanh(self.B_t1))
    else:
        self.B = self.sigmoid(self.B1)
        self.B_t = self.B
        self.B_t1 = np.dot(self.B_t, self.B_RNN)
        print('this should only print once')
    self.C1 = np.dot(self.B, self.BC)
    self.C = self.sigmoid(self.C1)
    return self.C

def skip_backprop(self):
    self.B_t = self.B

def get_cost(self, C_real):
    #self.cost = 0.5*sum((C_real-self.C)**2)
    self.cost = 0.5*((C_real-self.C)**2)
    return self.cost

def RNN_backprop(self, C_real):
    BT = self.B[np.newaxis]
    delta3 = np.multiply(-(C_real-self.C), self.sigmoidPrime(self.C1))
    BCp = np.dot(BT.T, delta3)
    BCpT = BCp[np.newaxis]

    delta2 = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B1)
    AT, d2 = self.A[np.newaxis], delta2[np.newaxis]
    ABp = np.dot(AT.T, d2)

    delta2t = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B_t1)
    B_RNNT, d2t = self.B_t[np.newaxis], delta2t[np.newaxis]
    B_RNNp = np.dot(B_RNNT.T, d2t)

    #Important
    #weight_multiplier = 5 * (np.sum(np.absolute(ABp))+np.sum(np.absolute(BCpT))+np.sum(np.absolute(B_RNNp)))
    weight_multiplier = 0.01

    self.BC = self.BC - BCpT.T*weight_multiplier
    self.AB = self.AB - ABp*weight_multiplier
    self.B_RNN = self.B_RNN - B_RNNp*weight_multiplier

    self.B_t = self.B

NN = NN()
NN.init_weights()

#important
iterations = 100000
for a in range(iterations):
    total_error = 0
    for i in range(50):
        NN.RNN_forward(np.array(As[i]))
        NN.RNN_backprop(C_reals[i])
        total_error += NN.get_cost(C_reals[i])
    if a%500 == 0:
        print("Error: ",total_error)
NN.RNN_forward(np.array([1,1,1,0.2]))
NN.skip_backprop()
print("0.4: ", NN.RNN_forward(np.array([1,1,1,0.3])))
NN.RNN_forward(np.array([1,1,1,0.4]))
NN.skip_backprop()
print("0.2: ", NN.RNN_forward(np.array([1,1,1,0.3])))
</code>```

答:
One common approach to eliminate this kind of behavior is to reduce the learning rate as you continue training.
While I can't explain it, adding batch normalization helped me to solve this problem in one case. But I could later get rid of it after increasing the capacity of the network.</p>

Body:
I've been trying to create a vanilla 3 layer RNN in Python 3.6, but whenever I train it the training loss decreases for the first X amount of training iterations then goes up and down sporadically and I can't identify the problem. I don't want to use Tensorflow or Keras or any deep learning framework for now because I'm trying to get a better understanding of how these NNs work.

I'm pretty sure my problem lies either in the way I added matrices together in my forward prop function, or in my get error and weight update part of my backprop function so I will post them both below.

Sorry if my code is a bit messy but here is my function that forward props through my neural network.

def RNN_forward(self, A):

    #input layer
    self.A = A

    #self.AB is a-b weight matrix
    self.B1 = np.dot(self.A, self.AB)

    #self.B_t is self.B (layer 2) from the previous timestep
    self.B_t1 = np.dot(self.B_t, self.B_RNN)

    #combining matrices
    self.B = self.sigmoid((self.B1) + (self.B_t1))
    self.C1 = np.dot(self.B, self.BC)

    #output layer
    self.C = self.sigmoid(self.C1)
    return self.C

My backprop and update weight matrix functions are mushed into one function, sorry everything is so messy

def RNN_backprop(self, C_real):

    #did this so I could transpose a 1D matrix
    BT = self.B[np.newaxis]

    #get error of BC weight matrix
    delta3 = np.multiply(-(C_real-self.C), self.sigmoidPrime(self.C1))
    BCp = np.dot(BT.T, delta3)
    BCpT = BCp[np.newaxis]

    #get error of AB weight matrix
    delta2 = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B1)
    AT, d2 = self.A[np.newaxis], delta2[np.newaxis]
    ABp = np.dot(AT.T, d2)

    #get error of weight matrix linked to previous time step
    delta2t = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B_t1)
    B_RNNT, d2t = self.B_t[np.newaxis], delta2t[np.newaxis]
    B_RNNp = np.dot(B_RNNT.T, d2t)

    #training speed
    weight_multiplier = 10

    #update weight matricies
    self.BC = self.BC - BCpT.T*weight_multiplier
    self.AB = self.AB - ABp*weight_multiplier
    self.B_RNN = self.B_RNN - B_RNNp*weight_multiplier

    #store layer 2 to be used in next timestep
    self.B_t = self.B

I am happy to post the entire code or any other bits that anyone might need to help diagnose my problem.

Thanks in advance for any advice or potential solutions you might have!

Edit:  Here is the entire code: it is really poorly commented so it's going to be difficult to read it but its all here. Some lines are commented out just because I wasn't sure if I was going to try and use them or not.

import numpy as np

class NN(object):

def __init__(self):
    self.A_size = 4
    self.B_size = 6
    self.C_size = 1

def init_weights(self):
    self.AB = np.random.randn(self.A_size, self.B_size)
    self.BC = np.random.randn(self.B_size, self.C_size)
    self.B_t = [0]
    self.B_RNN = np.random.randn(self.B_size, self.B_size)

def sigmoid(self, X1):
    return 1/(1+np.exp(-X1))

def sigmoidPrime(self,X1):
    return np.exp(-X1)/((1+np.exp(-X1))**2)

def print_status(self, NN_type):
    print("---------Status---------")
    print("A: ", self.A)
    print("AB: ", self.AB)
    print("B: ", self.B)
    print("BC: ", self.BC)
    print("C: ", self.C)
    if NN_type == "RNN":
        print("Previous B: ", self.B_t)
    if NN_type == "LSTM":
        pass
    #print("Error: ", self.cost)
    print("---------Done---------")

def RNN_forward(self, A):
    self.A = A
    self.B1 = np.dot(self.A, self.AB)
    if len(self.B_t) > 2:
        self.B_t1 = np.dot(self.B_t, self.B_RNN)
        self.B = self.sigmoid((self.B1) + (self.B_t1))
        #self.B = self.sigmoid(np.tanh(self.B1) + np.tanh(self.B_t1))
    else:
        self.B = self.sigmoid(self.B1)
        self.B_t = self.B
        self.B_t1 = np.dot(self.B_t, self.B_RNN)
        print('this should only print once')
    self.C1 = np.dot(self.B, self.BC)
    self.C = self.sigmoid(self.C1)
    return self.C

def skip_backprop(self):
    self.B_t = self.B

def get_cost(self, C_real):
    #self.cost = 0.5*sum((C_real-self.C)**2)
    self.cost = 0.5*((C_real-self.C)**2)
    return self.cost

def RNN_backprop(self, C_real):
    BT = self.B[np.newaxis]
    delta3 = np.multiply(-(C_real-self.C), self.sigmoidPrime(self.C1))
    BCp = np.dot(BT.T, delta3)
    BCpT = BCp[np.newaxis]

    delta2 = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B1)
    AT, d2 = self.A[np.newaxis], delta2[np.newaxis]
    ABp = np.dot(AT.T, d2)

    delta2t = np.dot(delta3, self.BC.T)*self.sigmoidPrime(self.B_t1)
    B_RNNT, d2t = self.B_t[np.newaxis], delta2t[np.newaxis]
    B_RNNp = np.dot(B_RNNT.T, d2t)

    #Important
    #weight_multiplier = 5 * (np.sum(np.absolute(ABp))+np.sum(np.absolute(BCpT))+np.sum(np.absolute(B_RNNp)))
    weight_multiplier = 0.01

    self.BC = self.BC - BCpT.T*weight_multiplier
    self.AB = self.AB - ABp*weight_multiplier
    self.B_RNN = self.B_RNN - B_RNNp*weight_multiplier

    self.B_t = self.B

NN = NN()
NN.init_weights()

#important
iterations = 100000
for a in range(iterations):
    total_error = 0
    for i in range(50):
        NN.RNN_forward(np.array(As[i]))
        NN.RNN_backprop(C_reals[i])
        total_error += NN.get_cost(C_reals[i])
    if a%500 == 0:
        print("Error: ",total_error)
NN.RNN_forward(np.array([1,1,1,0.2]))
NN.skip_backprop()
print("0.4: ", NN.RNN_forward(np.array([1,1,1,0.3])))
NN.RNN_forward(np.array([1,1,1,0.4]))
NN.skip_backprop()
print("0.2: ", NN.RNN_forward(np.array([1,1,1,0.3])))


问:
Multipart upload to Amazon Glacier: Content-Range incompatible with Content-Length
I'm trying to upload a file around 1gb in size to Amazon Glacier. Somewhat arbitrarily, I've decided to break it into 32mb parts and upload them in serial.

import math
import boto3
from botocore.utils import calculate_tree_hash

client = boto3.client('glacier')
vault_name = 'my-vault'
size = 1073745600 # in bytes
size_mb = size / (2**20) # Convert to megabytes for readability
local_file = 'filename'

multi_up = client.initiate_multipart_upload(vaultName=vault_name,
                                        archiveDescription=local_file,
                                        partSize=str(2**25)) # 32 mb in bytes
parts = math.floor(size_mb / 32)
with open("/Users/alexchase/Desktop/{}".format(local_file), 'rb') as upload:
    for p in range(parts):
        # Calculate lower and upper bounds for the byte ranges. The last range
        # is bigger than the ones that come before.
        lower = (p * (2**25))
        upper = (((p + 1) * (2**25)) - 1) if (p + 1 < parts) else (size)
        up_part = client.upload_multipart_part(vaultName=vault_name,
                                           uploadId=multi_up['uploadId'],
                                           range='bytes {}-{}/*'.format(lower, upper),
                                           body=upload)
checksum = calculate_tree_hash(upload)
complete_up = client.complete_multipart_upload(archiveSize=str(size),
                                               checksum=checksum,
                                               uploadId=multi_up['uploadId'],
                                               vaultName=vault_name)
```

<p>This generates an error about the first byte range.</p>

<pre class="lang-py prettyprint-override"><code>---------------------------------------------------------------------------
InvalidParameterValueException            Traceback (most recent call last)
<ipython-input-2-9dd3ac986601> in <module>()
     93                         uploadId=multi_up['uploadId'],
     94                         range='bytes {}-{}/*'.format(lower, upper),
---> 95                         body=upload)
     96                     upload_info.append(up_part)
     97                 checksum = calculate_tree_hash(upload)

~/anaconda/lib/python3.5/site-packages/botocore/client.py in _api_call(self, *args, **kwargs)
    251                     "%s() only accepts keyword arguments." % py_operation_name)
    252             # The "self" in this scope is referring to the BaseClient.
--> 253             return self._make_api_call(operation_name, kwargs)
    254
    255         _api_call.__name__ = str(py_operation_name)

~/anaconda/lib/python3.5/site-packages/botocore/client.py in _make_api_call(self, operation_name, api_params)
    555             error_code = parsed_response.get("Error", {}).get("Code")
    556             error_class = self.exceptions.from_code(error_code)
--> 557             raise error_class(parsed_response, operation_name)
    558         else:
    559             return parsed_response

InvalidParameterValueException: An error occurred (InvalidParameterValueException) when calling the UploadMultipartPart operation:
Content-Range: bytes 0-33554431/* is incompatible with Content-Length: 1073745600
</code>```

Can anyone see what I'm doing wrong?

答:
```<code>Content-Range: bytes 0-33554431/* is incompatible with Content-Length: 1073745600
</code>```

You're telling the API that you're sending the first 32 MiB, but you're actually sending (proposing to send) the entire file, since body=upload and upload isn't just the first part, it's the entire file.  The Content-Length refers to the size of this part upload, which should be 33554432 (32 MiB).

The docs are admittedly ambiguous...

body (bytes or seekable file-like object) -- The data to upload.

...but the "data to upload" seems to refer to the data for only this part, in spite of the word "seekable."

Body:
I'm trying to upload a file around 1gb in size to Amazon Glacier. Somewhat arbitrarily, I've decided to break it into 32mb parts and upload them in serial.

import math
import boto3
from botocore.utils import calculate_tree_hash

client = boto3.client('glacier')
vault_name = 'my-vault'
size = 1073745600 # in bytes
size_mb = size / (2**20) # Convert to megabytes for readability
local_file = 'filename'

multi_up = client.initiate_multipart_upload(vaultName=vault_name,
                                        archiveDescription=local_file,
                                        partSize=str(2**25)) # 32 mb in bytes
parts = math.floor(size_mb / 32)
with open("/Users/alexchase/Desktop/{}".format(local_file), 'rb') as upload:
    for p in range(parts):
        # Calculate lower and upper bounds for the byte ranges. The last range
        # is bigger than the ones that come before.
        lower = (p * (2**25))
        upper = (((p + 1) * (2**25)) - 1) if (p + 1 < parts) else (size)
        up_part = client.upload_multipart_part(vaultName=vault_name,
                                           uploadId=multi_up['uploadId'],
                                           range='bytes {}-{}/*'.format(lower, upper),
                                           body=upload)
checksum = calculate_tree_hash(upload)
complete_up = client.complete_multipart_upload(archiveSize=str(size),
                                               checksum=checksum,
                                               uploadId=multi_up['uploadId'],
                                               vaultName=vault_name)

This generates an error about the first byte range.

---------------------------------------------------------------------------
InvalidParameterValueException            Traceback (most recent call last)
<ipython-input-2-9dd3ac986601> in <module>()
     93                         uploadId=multi_up['uploadId'],
     94                         range='bytes {}-{}/*'.format(lower, upper),
---> 95                         body=upload)
     96                     upload_info.append(up_part)
     97                 checksum = calculate_tree_hash(upload)

~/anaconda/lib/python3.5/site-packages/botocore/client.py in _api_call(self, *args, **kwargs)
    251                     "%s() only accepts keyword arguments." % py_operation_name)
    252             # The "self" in this scope is referring to the BaseClient.
--> 253             return self._make_api_call(operation_name, kwargs)
    254
    255         _api_call.__name__ = str(py_operation_name)

~/anaconda/lib/python3.5/site-packages/botocore/client.py in _make_api_call(self, operation_name, api_params)
    555             error_code = parsed_response.get("Error", {}).get("Code")
    556             error_class = self.exceptions.from_code(error_code)
--> 557             raise error_class(parsed_response, operation_name)
    558         else:
    559             return parsed_response

InvalidParameterValueException: An error occurred (InvalidParameterValueException) when calling the UploadMultipartPart operation:
Content-Range: bytes 0-33554431/* is incompatible with Content-Length: 1073745600

Can anyone see what I'm doing wrong?

Body:
Content-Range: bytes 0-33554431/* is incompatible with Content-Length: 1073745600

You're telling the API that you're sending the first 32 MiB, but you're actually sending (proposing to send) the entire file, since body=upload and upload isn't just the first part, it's the entire file.  The Content-Length refers to the size of this part upload, which should be 33554432 (32 MiB).

The docs are admittedly ambiguous...

body (bytes or seekable file-like object) -- The data to upload.

...but the "data to upload" seems to refer to the data for only this part, in spite of the word "seekable."


问:
JIRA: Create API documents
Is it possible to create API documents on JIRA? If yes then how? The currently employed approach involves creating / updating a Microsoft Word document and replacing it on Confluence. This approach though fulfills the requirement but do not seems a better way for API documentation management.

Thanks

答:
Uploading Microsoft Word documents is probably the worst way.

Although I find Confluence (and JIRA) to be terrible, I write API docs using a table and it works well:

Once you have a template, copy and paste to grow the docs.

Title: JIRA: Create API documents


问:
setCharAt method not working as expected inside for loop (Java)
I am trying to develop a method to reverse the vowels in a string. For this, I have developed my own small stack. I am iterating backwards through the string twice, once to populate the stack with each vowel I locate, the second time to replace the vowel with the vowel stored at the top of the stack. I have added a bunch of print statements to determine where this is failing and it seems to be failing at the setCharAt method. For testing purposes, I provide a string aeiou and I am expecting to get back uoiea. The chars are getting replaced during each iteration, but unfortunately, they don't stay that way. As of the next iteration, the chars that were replaced on the previous iteration return to what they were before. As a result, I am getting back ueiou, where only the first character in the string is as expected (and the third which is a noop). Here is my code. Any tips are appreciated.

```<code>import java.util.*;

public class Solution {

    static String result;

    static class StackOfVowels {
        static Node top;

        public StackOfVowels() {
            Node top = null;
        }

        static class Node {
            Node next = null;
            char vowel = '\0';
            Node(char value) {
                this.vowel = value;
            }
        }

        public void push(char item) {
            Node node = new Node(item);
            if (top == null) {
                top = node;
            }
            else {
                node.next = top;
                top = node;
            }
        }

        public char top() {
            if (top == null) throw new EmptyStackException();
            return top.vowel;
        }

        public void pop() {
            int result = -1;
            if (top != null) {
                result = top.vowel;
                top = top.next;
            }
        }
    }

    public static String reverseVowels(String s) {

        StackOfVowels stackOfVowels = new StackOfVowels();

        for(int i = s.length()-1; i >= 0; i--) {
            char c = s.charAt(i);
            if ((c == 'a') || (c == 'e') || (c == 'i') || (c == 'o') || (c == 'u')) {
                System.out.println("Initial sequence of iterations identified vowel: " + c);
                stackOfVowels.push(c);
                System.out.println("Pushed to stack, current top is: " + stackOfVowels.top());
            }
        }

        for(int j = s.length()-1; j >= 0; j--) {
            char b = s.charAt(j);
            if ((b == 'a') || (b == 'e') || (b == 'i') || (b == 'o') || (b == 'u')) {
                System.out.println("Second sequence of iterations identified vowel: " + b);
                StringBuilder newstr = new StringBuilder(s);
                char d = stackOfVowels.top();
                System.out.println("Variable d set to top of: " + stackOfVowels.top());
                newstr.setCharAt(j, d);
                result = newstr.toString();
                System.out.println("Here is the new string: " + result);
                stackOfVowels.pop();
                System.out.println("Stack was popped");
            }
        }
        return result;
    }

    public static void main(String[] args) {
        String s = "aeiou";
        reverseVowels(s);
        System.out.println("Final result: " + result);
    }
}
</code>```

答:
I would approach the problem a little differently, first I would use a regular expression to remove all consonants from the String to create a String of vowels. Then I would iterate through the characters of the String, using StringBuilder to build the output (passing consonants through, but replacing vowels using the vowels String previously created). Like,

```<code>public static String reverseVowels(String s) {
    // Match all consonants, and remove them. Reverse that String.
    String vowels = new StringBuilder(s.replaceAll("[^AEIOUaeiou]", ""))
            .reverse().toString();
    StringBuilder sb = new StringBuilder();
    for (int i = 0, p = 0; i < s.length(); i++) {
        switch (Character.toLowerCase(s.charAt(i))) {
        // Note that these fall-through...
        case 'a': case 'e': case 'i': case 'o': case 'u':
            sb.append(vowels.charAt(p++));
            break;
        default:
            sb.append(s.charAt(i));
        }
    }
    return sb.toString();
}
</code>```

This is one of the places that switch and fall-through behavior can be taken advantage of.

And if you're using Java 8+, you could express the same with an IntStream and map the characters; like

```<code>String vowels = new StringBuilder(s.replaceAll("[^AEIOUaeiou]", ""))
        .reverse().toString();
int[] counter = new int[1]; // <-- A bit of a kludge really.
return IntStream.range(0, s.length()).mapToObj(i -> {
    switch (Character.toLowerCase(s.charAt(i))) {
    case 'a': case 'e': case 'i': case 'o': case 'u':
        return Character.toString(vowels.charAt(counter[0]++));
    default:
        return Character.toString(s.charAt(i));
    }
}).collect(Collectors.joining());
</code>```

Body:
I am trying to develop a method to reverse the vowels in a string. For this, I have developed my own small stack. I am iterating backwards through the string twice, once to populate the stack with each vowel I locate, the second time to replace the vowel with the vowel stored at the top of the stack. I have added a bunch of print statements to determine where this is failing and it seems to be failing at the setCharAt method. For testing purposes, I provide a string aeiou and I am expecting to get back uoiea. The chars are getting replaced during each iteration, but unfortunately, they don't stay that way. As of the next iteration, the chars that were replaced on the previous iteration return to what they were before. As a result, I am getting back ueiou, where only the first character in the string is as expected (and the third which is a noop). Here is my code. Any tips are appreciated.

import java.util.*;

public class Solution {

    static String result;

    static class StackOfVowels {
        static Node top;

        public StackOfVowels() {
            Node top = null;
        }

        static class Node {
            Node next = null;
            char vowel = '\0';
            Node(char value) {
                this.vowel = value;
            }
        }

        public void push(char item) {
            Node node = new Node(item);
            if (top == null) {
                top = node;
            }
            else {
                node.next = top;
                top = node;
            }
        }

        public char top() {
            if (top == null) throw new EmptyStackException();
            return top.vowel;
        }

        public void pop() {
            int result = -1;
            if (top != null) {
                result = top.vowel;
                top = top.next;
            }
        }
    }

    public static String reverseVowels(String s) {

        StackOfVowels stackOfVowels = new StackOfVowels();

        for(int i = s.length()-1; i >= 0; i--) {
            char c = s.charAt(i);
            if ((c == 'a') || (c == 'e') || (c == 'i') || (c == 'o') || (c == 'u')) {
                System.out.println("Initial sequence of iterations identified vowel: " + c);
                stackOfVowels.push(c);
                System.out.println("Pushed to stack, current top is: " + stackOfVowels.top());
            }
        }

        for(int j = s.length()-1; j >= 0; j--) {
            char b = s.charAt(j);
            if ((b == 'a') || (b == 'e') || (b == 'i') || (b == 'o') || (b == 'u')) {
                System.out.println("Second sequence of iterations identified vowel: " + b);
                StringBuilder newstr = new StringBuilder(s);
                char d = stackOfVowels.top();
                System.out.println("Variable d set to top of: " + stackOfVowels.top());
                newstr.setCharAt(j, d);
                result = newstr.toString();
                System.out.println("Here is the new string: " + result);
                stackOfVowels.pop();
                System.out.println("Stack was popped");
            }
        }
        return result;
    }

    public static void main(String[] args) {
        String s = "aeiou";
        reverseVowels(s);
        System.out.println("Final result: " + result);
    }
}

Body:
I would approach the problem a little differently, first I would use a regular expression to remove all consonants from the String to create a String of vowels. Then I would iterate through the characters of the String, using StringBuilder to build the output (passing consonants through, but replacing vowels using the vowels String previously created). Like,

public static String reverseVowels(String s) {
    // Match all consonants, and remove them. Reverse that String.
    String vowels = new StringBuilder(s.replaceAll("[^AEIOUaeiou]", ""))
            .reverse().toString();
    StringBuilder sb = new StringBuilder();
    for (int i = 0, p = 0; i < s.length(); i++) {
        switch (Character.toLowerCase(s.charAt(i))) {
        // Note that these fall-through...
        case 'a': case 'e': case 'i': case 'o': case 'u':
            sb.append(vowels.charAt(p++));
            break;
        default:
            sb.append(s.charAt(i));
        }
    }
    return sb.toString();
}

This is one of the places that switch and fall-through behavior can be taken advantage of.

And if you're using Java 8+, you could express the same with an IntStream and map the characters; like

String vowels = new StringBuilder(s.replaceAll("[^AEIOUaeiou]", ""))
        .reverse().toString();
int[] counter = new int[1]; // <-- A bit of a kludge really.
return IntStream.range(0, s.length()).mapToObj(i -> {
    switch (Character.toLowerCase(s.charAt(i))) {
    case 'a': case 'e': case 'i': case 'o': case 'u':
        return Character.toString(vowels.charAt(counter[0]++));
    default:
        return Character.toString(s.charAt(i));
    }
}).collect(Collectors.joining());


问:
google sign in implementation in codeigniter google return response code with "/" in value which break the code
this is my controller for google login . code does't work after google response code.

```<code>   public function index(){
    // Include the google api php libraries
    require_once APPPATH.'libraries/google-api-php-client/vendor/autoload.php';

    // Google Project API Credentials
    $clientId = 'mentioned';
    $clientSecret = 'mentioned';
    $redirectUrl = base_url() . 'user_authentication/';

    // Google Client Configuration
        $gClient = new Google_Client();
        $gClient->addScope('email');
        $gClient->setApplicationName('REDBUD HOTELS');
        $gClient->setClientId($clientId);
        $gClient->setClientSecret($clientSecret);
        $gClient->setRedirectUri($redirectUrl);
        $google_oauthV2 = new Google_Service($gClient);
//GOOGLE response
        if (isset($_REQUEST['code']))
                  {
                    $gClient->authenticate($_REQUEST['code']);
                    $this->session->set_userdata('token', $gClient->getAccessToken());
                    header('Location: http://' . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']);

                  }
 //check if $token us set
        $token = $this->session->userdata('token');
        if (!empty($token))
            {
            $gClient->setAccessToken($token);
            }

        if ($gClient->getAccessToken())
            {
            $userProfile = $plus->userinfo->get();
            // Preparing data for database insertion
            $userData['oauth_provider'] = 'google';
            $userData['oauth_uid'] = $userProfile['id'];
            $userData['first_name'] = $userProfile['given_name'];
            $userData['last_name'] = $userProfile['family_name'];
            $userData['email'] = $userProfile['email'];
            $userData['gender'] = $userProfile['gender'];
            $userData['locale'] = $userProfile['locale'];
            $userData['profile_url'] = $userProfile['link'];
            $userData['picture_url'] = $userProfile['picture'];
            // Insert or update user data
            $userID = $this->user->checkUser($userData);
            if(!empty($userID))
            {
                $data['userData'] = $userData;
                $this->session->set_userdata('userData',$userData);
            } else
            {
               $data['userData'] = array();
            }
        } else
         {
            $data['authUrl'] = $gClient->createAuthUrl();
         }
        $this->load->view('user_authentication/index',$data);
    }
</code>```

"response Code From Google user_authentication/?code=4/5wcPW5Yv6qNONOzeUz5gun4PtfuPTa6mPN9r97BDhGM# "
please also tell me what should be better  $plus->userinfo->get() or $google_oauthV2->userinfo->get();

答:
google response code does have "/"

ex: http://www.example.com/storage_integration/granted?code=4/oXKtlTyfmtzUBc5CjbafSpwItMz7itZMhM54VpKEbwI

you can use $_GET instead of $_REQUEST

```<code>if (isset($_GET['code'])) {
   // authenticate auth code here
}
</code>```

Body:
this is my controller for google login . code does't work after google response code.

   public function index(){
    // Include the google api php libraries
    require_once APPPATH.'libraries/google-api-php-client/vendor/autoload.php';

    // Google Project API Credentials
    $clientId = 'mentioned';
    $clientSecret = 'mentioned';
    $redirectUrl = base_url() . 'user_authentication/';

    // Google Client Configuration
        $gClient = new Google_Client();
        $gClient->addScope('email');
        $gClient->setApplicationName('REDBUD HOTELS');
        $gClient->setClientId($clientId);
        $gClient->setClientSecret($clientSecret);
        $gClient->setRedirectUri($redirectUrl);
        $google_oauthV2 = new Google_Service($gClient);
//GOOGLE response
        if (isset($_REQUEST['code']))
                  {
                    $gClient->authenticate($_REQUEST['code']);
                    $this->session->set_userdata('token', $gClient->getAccessToken());
                    header('Location: http://' . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF']);

                  }
 //check if $token us set
        $token = $this->session->userdata('token');
        if (!empty($token))
            {
            $gClient->setAccessToken($token);
            }

        if ($gClient->getAccessToken())
            {
            $userProfile = $plus->userinfo->get();
            // Preparing data for database insertion
            $userData['oauth_provider'] = 'google';
            $userData['oauth_uid'] = $userProfile['id'];
            $userData['first_name'] = $userProfile['given_name'];
            $userData['last_name'] = $userProfile['family_name'];
            $userData['email'] = $userProfile['email'];
            $userData['gender'] = $userProfile['gender'];
            $userData['locale'] = $userProfile['locale'];
            $userData['profile_url'] = $userProfile['link'];
            $userData['picture_url'] = $userProfile['picture'];
            // Insert or update user data
            $userID = $this->user->checkUser($userData);
            if(!empty($userID))
            {
                $data['userData'] = $userData;
                $this->session->set_userdata('userData',$userData);
            } else
            {
               $data['userData'] = array();
            }
        } else
         {
            $data['authUrl'] = $gClient->createAuthUrl();
         }
        $this->load->view('user_authentication/index',$data);
    }

"response Code From Google user_authentication/?code=4/5wcPW5Yv6qNONOzeUz5gun4PtfuPTa6mPN9r97BDhGM# "
please also tell me what should be better  $plus->userinfo->get() or $google_oauthV2->userinfo->get();

Body:
google response code does have "/"

ex: http://www.example.com/storage_integration/granted?code=4/oXKtlTyfmtzUBc5CjbafSpwItMz7itZMhM54VpKEbwI

you can use $_GET instead of $_REQUEST

if (isset($_GET['code'])) {
   // authenticate auth code here
}


问:
How to get updated data after editing through post request in angular 2
I have searched a lot on this but cannot understand how to get updated data from database. I am learning angular 2 and my situation is that I am fetching the data from table named branches using php in angular 2. Here is my Service in angular 2 project

```<code>import { Injectable } from '@angular/core';
import {Http, Headers, Response} from "@angular/http";
import "rxjs/add/operator/map";
import "rxjs/add/operator/catch";
import "rxjs/add/observable/throw";
import { Observable } from "rxjs/Observable";

@Injectable()
export class BranchesService {

  constructor(private _http: Http){}
  _errorHandler(error: Response){
    console.error(error);
    return Observable.throw(error || "Internal server error");
  }

  getBranches(limit, offset){
    console.log("I am called");
    return this._http.get("http://localhost/churchDb/api/v1/branches/"+limit+"/"+offset)
                .map((response: Response) => response.json())
                .catch(this._errorHandler);
  }

  updateBranch(value){
    let headers = new Headers();
    headers.append("Content-Type","application/json; charset=utf-8");
    return this._http.post("http://localhost/churchDb/api/v1/update-branch", value , headers )
      .map((response: Response) =>
        response.json()
      )
      .catch(this._errorHandler);
  }

}
</code>```

And in my branches Component I am subscribing to getBranches in branches service

```<code>branches=[];
ngOnInit() {
    this.branches=[];
    this.sub=this._branchesService.getBranches(this.limit,this.offset)
      .subscribe(
        (resBranchesData)=> {
          this.errorMsg=resBranchesData.message;
          this.branches=resBranchesData.data;
          console.log("Updated : " + JSON.stringify(resBranchesData));
        },
        (resBranchesError)=>{
          console.log(resBranchesError)
        }
      );
  }
</code>```

And displaying branches in my View

```<code><table class="table table-bordered">
      <thead>
        <tr>
          <th>#</th>
          <th>First Name</th>
          <th>Address</th>
          <th>City</th>
          <th>Actions</th>
          <!--<th>Username</th>-->
        </tr>
      </thead>
      <tbody *ngFor="let branch of branches" style="text-align: left">
        <tr>
          <td>{{ branch.id }}</td>
          <td>{{ branch.name }}</td>
          <td>{{ branch.address }}</td>

          <div *ngFor="let city of cities">
            <td *ngIf="city.id == branch.city" style="border:none">
              {{ city.name }}
            </td>
          </div>
          <td><button class="btn btn-default" (click)="edit(branch)" >edit</button><button class="btn btn-danger" (click)="openModal()" style="margin-left: 10px">delete</button></td>
        </tr>
      </tbody>
    </table>
</code>```

On clicking edit I display a pre-filed form in modal in the same view

```<code><modal [animation]="animation" [keyboard]="keyboard" [backdrop]="backdrop" [cssClass]="cssClass" #modal>
  <form #branchEditForm="ngForm"  (ngSubmit)="updateBranch(branchEditForm.value)">
    <modal-header [show-close]="true">
      <h4 class="modal-title">Add Church Branch</h4>
    </modal-header>
    <modal-body>
      <div class="form-group">
        <input type="hidden" class="form-control" required name="id" id="id" ngModel="{{branch.id}}">
        <label>Church Name</label>
        <input type="text" class="form-control" required name="name" id="name" ngModel="{{branch.name}}">
      </div>
      <div class="form-group">
        <label>Address</label>
        <input type="text" class="form-control" required name="address" id="address" ngModel="{{branch.address}}">
      </div>
      <div class="form-group">
        <label>Address</label>
        <select class="form-control" name="city" ngModel="{{branch.city}}">
            <option *ngFor="let city of cities" value="{{city.id}}" [attr.selected]="city.id == branch.city ? '' : selected" >{{city.name}}</option>
        </select>
      </div>

    </modal-body>
    <modal-footer>
      <button type="button" class="btn btn-default" data-dismiss="modal" (click)="modal.dismiss()">Cancel</button>
      <!--<button type="button" class="btn btn-primary" [disabled]="!modalForm.valid" (click)="validationModal.close()">Update</button>-->
      <input type="submit" class="btn btn-primary" [disabled]="!branchEditForm.valid" value="Update" />
    </modal-footer>
  </form>
</modal>
</code>```

Upon submitting the form in branches Component

```<code>updateBranch(value:any){
    console.log(value);
    this._branchesService.updateBranch(value)
      .subscribe(
        (response)=>{
          if(response.code == "200"){
            this.modal.close();
            this._router.navigate(['branches']);
          }else{
            // this.showFlag=true;
            // this.loadingFlag=false;
            // this.error=response.message;
          }
        },
        (error) =>{ this.error=error }
      )
  }
</code>```

The above function successfully updates the data in database table but I cant get the updated data in branches Service.
I see the updated data only after clearing the cache of my browser.
I have also tried navigating from a different component with no luck.
I have also figured if the url in post request is changed, it gets me updated data.
What am I doing wrong? I am new to angular 2 and cannot figure the reason. Any help is much appreciated.

答:
I am not fixing your code, instead I'm showing you the principles.
Consider this:

Service method:

```<code>updateBranch(branch: IBranch): Observable<IBranch> {
    return this.http.post(this.YOUR_URL, branch)
        .map(resp => resp.json() as IBranch);
}
</code>```

updateBranch method will return an observable of IBranch type (you can also use "any" if you want, without using the interface)
            On your server side of course, you need to send back the updated model in the json format. This data will be mapped to the IBranch
            model (or any) once the request is done.

IBranch interface:

```<code>interface IBranch {
    Id: number;
    Name: string;
    Address: string;
 }
</code>```

IBranch Component model:

```<code>branchModel: IBranch;
</code>```

Now when you subscribe to the updateBranch method, updated model that server returned will be assigned to
        your branchModel.

Component's update method:

```<code>updateBranch(branch: IBranch): void {
    this.branchService.updateBranch(branch)
      .subscribe(response => this.branchModel = response);
 }
</code>```

Body:
I have searched a lot on this but cannot understand how to get updated data from database. I am learning angular 2 and my situation is that I am fetching the data from table named branches using php in angular 2. Here is my Service in angular 2 project

import { Injectable } from '@angular/core';
import {Http, Headers, Response} from "@angular/http";
import "rxjs/add/operator/map";
import "rxjs/add/operator/catch";
import "rxjs/add/observable/throw";
import { Observable } from "rxjs/Observable";

@Injectable()
export class BranchesService {

  constructor(private _http: Http){}
  _errorHandler(error: Response){
    console.error(error);
    return Observable.throw(error || "Internal server error");
  }

  getBranches(limit, offset){
    console.log("I am called");
    return this._http.get("http://localhost/churchDb/api/v1/branches/"+limit+"/"+offset)
                .map((response: Response) => response.json())
                .catch(this._errorHandler);
  }

  updateBranch(value){
    let headers = new Headers();
    headers.append("Content-Type","application/json; charset=utf-8");
    return this._http.post("http://localhost/churchDb/api/v1/update-branch", value , headers )
      .map((response: Response) =>
        response.json()
      )
      .catch(this._errorHandler);
  }

}

And in my branches Component I am subscribing to getBranches in branches service

branches=[];
ngOnInit() {
    this.branches=[];
    this.sub=this._branchesService.getBranches(this.limit,this.offset)
      .subscribe(
        (resBranchesData)=> {
          this.errorMsg=resBranchesData.message;
          this.branches=resBranchesData.data;
          console.log("Updated : " + JSON.stringify(resBranchesData));
        },
        (resBranchesError)=>{
          console.log(resBranchesError)
        }
      );
  }

And displaying branches in my View

          #
          First Name
          Address
          City
          Actions

          {{ branch.id }}
          {{ branch.name }}
          {{ branch.address }}

              {{ city.name }}

          <button class="btn btn-default" (click)="edit(branch)" >edit</button><button class="btn btn-danger" (click)="openModal()" style="margin-left: 10px">delete</button>

On clicking edit I display a pre-filed form in modal in the same view

<modal [animation]="animation" [keyboard]="keyboard" [backdrop]="backdrop" [cssClass]="cssClass" #modal>
  <form #branchEditForm="ngForm"  (ngSubmit)="updateBranch(branchEditForm.value)">
    <modal-header [show-close]="true">

Add Church Branch

    </modal-header>
    <modal-body>

        <input type="hidden" class="form-control" required name="id" id="id" ngModel="{{branch.id}}">
        Church Name
        <input type="text" class="form-control" required name="name" id="name" ngModel="{{branch.name}}">

        Address
        <input type="text" class="form-control" required name="address" id="address" ngModel="{{branch.address}}">

        Address
        <select class="form-control" name="city" ngModel="{{branch.city}}">
            <option *ngFor="let city of cities" value="{{city.id}}" [attr.selected]="city.id == branch.city ? '' : selected" >{{city.name}}</option>
        </select>

    </modal-body>
    <modal-footer>
      <button type="button" class="btn btn-default" data-dismiss="modal" (click)="modal.dismiss()">Cancel</button>

      <input type="submit" class="btn btn-primary" [disabled]="!branchEditForm.valid" value="Update" />
    </modal-footer>
  </form>
</modal>

Upon submitting the form in branches Component

updateBranch(value:any){
    console.log(value);
    this._branchesService.updateBranch(value)
      .subscribe(
        (response)=>{
          if(response.code == "200"){
            this.modal.close();
            this._router.navigate(['branches']);
          }else{
            // this.showFlag=true;
            // this.loadingFlag=false;
            // this.error=response.message;
          }
        },
        (error) =>{ this.error=error }
      )
  }

The above function successfully updates the data in database table but I cant get the updated data in branches Service.
I see the updated data only after clearing the cache of my browser.
I have also tried navigating from a different component with no luck.
I have also figured if the url in post request is changed, it gets me updated data.
What am I doing wrong? I am new to angular 2 and cannot figure the reason. Any help is much appreciated.

Body:
I am not fixing your code, instead I'm showing you the principles.
Consider this:

Service method:

updateBranch(branch: IBranch): Observable<IBranch> {
    return this.http.post(this.YOUR_URL, branch)
        .map(resp => resp.json() as IBranch);
}

updateBranch method will return an observable of IBranch type (you can also use "any" if you want, without using the interface)
            On your server side of course, you need to send back the updated model in the json format. This data will be mapped to the IBranch
            model (or any) once the request is done.

IBranch interface:

interface IBranch {
    Id: number;
    Name: string;
    Address: string;
 }

IBranch Component model:

branchModel: IBranch;

Now when you subscribe to the updateBranch method, updated model that server returned will be assigned to
        your branchModel.

Component's update method:

updateBranch(branch: IBranch): void {
    this.branchService.updateBranch(branch)
      .subscribe(response => this.branchModel = response);
 }


问:
Git Merge Conflict Practises
I think this is a very small issue but I want to know if there's any actual documentation on the topic one way or another, or maybe even opinions with reasons why.

When dealing with merge conflicts is it better to

Commit the merge with ONLY the merge resolution using git, then
build and test and if you've made mistakes with the merge reset HEAD
back one and repeat merge resolutions so that the only things
changed can be traced back to either branch1 or branch2 but it might
take longer.

Resolve the conflicts, remain uncommitted, build and go to editor to fix merge mistakes manually in an IDE, once it builds
commit the merge. Quicker but not every change is traceable to a
branch.

There are many ways to skin a cat and it doesn't matter if
the change was or wasn't in either branch before the merge.

Another option not listed

答:
This is a really good question, and for the case of rebasing a branch it gets even more complicated.  A single rebase operation may involve recommitting multiple commits on top of a target branch.  Each one of these commits could potentially be introducing a bug.  I have never heard of someone doing a full build and test cycle for each commit in either a rebase or a merge.

I would say that best practice is to just make some number of additional commits after a merge or rebase which fixes the bug.  This way, you have a clean audit trail about what actually happened.  Having such a history also helps from a separation of concerns point of view.  If you ever needed to revert a post merge bug fix, using this approach it would be straightforward.  It would be more difficult if you were to roll the bug fix together with the merge commit.

Title: Git Merge Conflict Practises