问:
while loop and promises
I'm trying to better understand async behavior in terms of promises. I am trying to execute a promise using a forever while loop. I've already read several posts on how to do this but I want to understand why the following doesn't work.

promises.js

```<code>const promise = new Promise(function (resolve, reject) {
    resolve('success');
    reject('failed');
});

while (true) {
    promise.then((res) => {
        console.log(res);
    }).catch((err) => {
        console.log(err);
    });
}
</code>```

Expected:

```<code>$ node promises.js
success
success
success
success
...
</code>```

Here the ... means continuing forever.

Actual:

```<code>$ node promises.js
FATAL ERROR: Ineffective mark-compacts near heap limit Allocation failed - JavaScript heap out of memory
 1: 00007FF7E2D7F04A v8::internal::GCIdleTimeHandler::GCIdleTimeHandler+5114
 2: 00007FF7E2D5A0C6 node::MakeCallback+4518
 3: 00007FF7E2D5AA30 node_module_register+2032
 4: 00007FF7E2FE20EE v8::internal::FatalProcessOutOfMemory+846
 5: 00007FF7E2FE201F v8::internal::FatalProcessOutOfMemory+639
 6: 00007FF7E3502BC4 v8::internal::Heap::MaxHeapGrowingFactor+9556
 7: 00007FF7E34F9C46 v8::internal::ScavengeJob::operator=+24310
 8: 00007FF7E34F829C v8::internal::ScavengeJob::operator=+17740
 9: 00007FF7E3500F87 v8::internal::Heap::MaxHeapGrowingFactor+2327
10: 00007FF7E3501006 v8::internal::Heap::MaxHeapGrowingFactor+2454
11: 00007FF7E30BCDB7 v8::internal::Factory::NewFillerObject+55
12: 00007FF7E3152CC6 v8::internal::WasmJs::Install+29414
13: 000001BD351DC5C1
</code>```

Here the process just hangs then errors out.

My understanding is that because promises are async, using a standard while loop doesn't work. My guess is that the promises are being called (called as in promise.then(...).catch(...)) faster then they are being resolved?

What is causing the process to hang and then run out of heap memory?

答:
Consider this bit of code:

```<code>const promise = new Promise(function (resolve, reject) {
    resolve('success');
    reject('failed');
});

var x = 0
while (x < 50) {
    promise.then((res) => {
        console.log(res);
    }).catch((err) => {
        console.log(err);
    });
    x++;
}
</code>```

It's just like yours but it only runs the while loop 50 times. If you run this in chrome and set breakpoints, you'll find that first the promise variable is instantiated to the new Promise, and then the while loop starts, the line that says promise.then.. runs, and then...

And then what you were expecting to happen next was perhaps the function inside the .then would run, but no, due to the asynchronous nature of promises, and the synchronous nature of while, it goes to x++ and then back to promise.then... without ever running the internal function

The internal function is scheduled to run, but if the synchronous javascript never stops running, it never gets a chance to run. Javascript is single threaded, so your version of the loop keeps going forever and making more .then calls, filling up the stack and memory and breaking.

In my code, the function inside .then( runs AFTER x = 50, because that's when the while loop has ceased synchronously running.

edit

Consider, also, this bit of code:

```<code>var x = true;
function changeX(count) {
    return new Promise(resolve => {
        console.log('inside changeX');
        setTimeout(function() {
            if (count > 10) x = false;
            resolve();
        },100);
    })
}

async function run() {
   var count = 0;
   while(x) {
       await changeX(count);
       count++;
   }
   console.log('x is false now');
}

run();
</code>```

Because this uses async await syntax, the while loop won't behave the same as your promises. If you run this through webpack/babel to convert it to es5 promises, you might find that it does something quite interesting.

Title: while loop and promises

Body:
I'm trying to better understand async behavior in terms of promises. I am trying to execute a promise using a forever while loop. I've already read several posts on how to do this but I want to understand why the following doesn't work.

promises.js

const promise = new Promise(function (resolve, reject) {
    resolve('success');
    reject('failed');
});

while (true) {
    promise.then((res) => {
        console.log(res);
    }).catch((err) => {
        console.log(err);
    });
}

Expected:

$ node promises.js
success
success
success
success
...

Here the ... means continuing forever.

Actual:

$ node promises.js
FATAL ERROR: Ineffective mark-compacts near heap limit Allocation failed - JavaScript heap out of memory
 1: 00007FF7E2D7F04A v8::internal::GCIdleTimeHandler::GCIdleTimeHandler+5114
 2: 00007FF7E2D5A0C6 node::MakeCallback+4518
 3: 00007FF7E2D5AA30 node_module_register+2032
 4: 00007FF7E2FE20EE v8::internal::FatalProcessOutOfMemory+846
 5: 00007FF7E2FE201F v8::internal::FatalProcessOutOfMemory+639
 6: 00007FF7E3502BC4 v8::internal::Heap::MaxHeapGrowingFactor+9556
 7: 00007FF7E34F9C46 v8::internal::ScavengeJob::operator=+24310
 8: 00007FF7E34F829C v8::internal::ScavengeJob::operator=+17740
 9: 00007FF7E3500F87 v8::internal::Heap::MaxHeapGrowingFactor+2327
10: 00007FF7E3501006 v8::internal::Heap::MaxHeapGrowingFactor+2454
11: 00007FF7E30BCDB7 v8::internal::Factory::NewFillerObject+55
12: 00007FF7E3152CC6 v8::internal::WasmJs::Install+29414
13: 000001BD351DC5C1

Here the process just hangs then errors out.

My understanding is that because promises are async, using a standard while loop doesn't work. My guess is that the promises are being called (called as in promise.then(...).catch(...)) faster then they are being resolved?

What is causing the process to hang and then run out of heap memory?

Body:
Consider this bit of code:

const promise = new Promise(function (resolve, reject) {
    resolve('success');
    reject('failed');
});

var x = 0
while (x < 50) {
    promise.then((res) => {
        console.log(res);
    }).catch((err) => {
        console.log(err);
    });
    x++;
}

It's just like yours but it only runs the while loop 50 times. If you run this in chrome and set breakpoints, you'll find that first the promise variable is instantiated to the new Promise, and then the while loop starts, the line that says promise.then.. runs, and then...

And then what you were expecting to happen next was perhaps the function inside the .then would run, but no, due to the asynchronous nature of promises, and the synchronous nature of while, it goes to x++ and then back to promise.then... without ever running the internal function

The internal function is scheduled to run, but if the synchronous javascript never stops running, it never gets a chance to run. Javascript is single threaded, so your version of the loop keeps going forever and making more .then calls, filling up the stack and memory and breaking.

In my code, the function inside .then( runs AFTER x = 50, because that's when the while loop has ceased synchronously running.

edit

Consider, also, this bit of code:

var x = true;
function changeX(count) {
    return new Promise(resolve => {
        console.log('inside changeX');
        setTimeout(function() {
            if (count > 10) x = false;
            resolve();
        },100);
    })
}

async function run() {
   var count = 0;
   while(x) {
       await changeX(count);
       count++;
   }
   console.log('x is false now');
}

run();

Because this uses async await syntax, the while loop won't behave the same as your promises. If you run this through webpack/babel to convert it to es5 promises, you might find that it does something quite interesting.


来源: stackexchange

问:
React front-end renders differently from state
I am building a react app which creates graphs. I Use react-d3-geaph for this. The graph takes its data from state like this:

```<code>   data: {
    nodes: [
         { "id": "1", "name": "connector"},
         { "id": "2", "name": "id1"},
         { "id": "3", "name": "node"}
     ],
     links: [
         {"source": "1" , "target": "2"},
         {"source": "3" , "target": "1"}
       ]
   }
</code>```

The rendered graph is the following:

What I am trying to achieve now, is to delete a link when the user clicks on it. react-d3-graph gives a method that returns the source and the target of the clicked link. So I have written the following function to find and delete the right link:

```<code>delLink(source, target) {

    var data = {...this.state.data};
    var dataArray = [...data.links];

    for(var i = 0; i < dataArray.length; i++) {
      if(dataArray[i].source === source && dataArray[i].target === target) {
        console.log(i);
        dataArray.splice(i, 1);
        data.links = dataArray;
        this.setState({data: data}, function () {
          console.log(this.state.data);
        });
      }
    }
   }
</code>```

This function achieves to find successfully the index of the state array and then delete it. While I console.log the new state I get the result I wish. For example, if I click the link from connector to id1 this is the new state:

```<code>data: {
    nodes: [
         { "id": "1", "name": "connector"},
         { "id": "2", "name": "id1"},
         { "id": "3", "name": "node"}
     ],
     links: [
         {"source": "3" , "target": "1"}
       ]
   }
</code>```

However, the problem is that, although the function works properly and erases the right index from the links array, the app renders a wrong graph with the wrong link deleted:

After some tries, I realized that whatever link I click the app will delete the last link from the link array.
Lastly, if I save the new graph through the app and refresh it, I get the right graph this time with a link between node and connector.

I believe it is a React issue regarding the asynchronous functionality but I can not figure out how I could solve it.

Please tell if you need any other information.
Thank you in advance!

答:
Array::splice mutates the array in place, you want to return an entirely new array of links with the deleted one filtered out.

array::splice mdn

I'm on mobile commuting now, but if you'd like I can provide an example to help illustrate.

[Edit] Oops, I see that you do copy the array first, but then you store it back in data, which is a reference to the previous state. Try spreading the previous state (and array because shallow copying) into a new data object, mutate the array there, and set state as normal.

Can you provide a codesandbox example for us to examine?

ContentLicense: CC BY-SA 4.0

Body:
I am building a react app which creates graphs. I Use react-d3-geaph for this. The graph takes its data from state like this:

   data: {
    nodes: [
         { "id": "1", "name": "connector"},
         { "id": "2", "name": "id1"},
         { "id": "3", "name": "node"}
     ],
     links: [
         {"source": "1" , "target": "2"},
         {"source": "3" , "target": "1"}
       ]
   }

The rendered graph is the following:

What I am trying to achieve now, is to delete a link when the user clicks on it. react-d3-graph gives a method that returns the source and the target of the clicked link. So I have written the following function to find and delete the right link:

delLink(source, target) {

    var data = {...this.state.data};
    var dataArray = [...data.links];

    for(var i = 0; i < dataArray.length; i++) {
      if(dataArray[i].source === source && dataArray[i].target === target) {
        console.log(i);
        dataArray.splice(i, 1);
        data.links = dataArray;
        this.setState({data: data}, function () {
          console.log(this.state.data);
        });
      }
    }
   }

This function achieves to find successfully the index of the state array and then delete it. While I console.log the new state I get the result I wish. For example, if I click the link from connector to id1 this is the new state:

data: {
    nodes: [
         { "id": "1", "name": "connector"},
         { "id": "2", "name": "id1"},
         { "id": "3", "name": "node"}
     ],
     links: [
         {"source": "3" , "target": "1"}
       ]
   }

However, the problem is that, although the function works properly and erases the right index from the links array, the app renders a wrong graph with the wrong link deleted:

After some tries, I realized that whatever link I click the app will delete the last link from the link array.
Lastly, if I save the new graph through the app and refresh it, I get the right graph this time with a link between node and connector.

I believe it is a React issue regarding the asynchronous functionality but I can not figure out how I could solve it.

Please tell if you need any other information.
Thank you in advance!


问:
New to objective-c. I don't understand the magic in writing methods without declaration in SenTestCase
I write my first simple unit tests and don't understand the magic objective c compiler. I can write unit test methods without declaring them in the test class .h file.

my test class remains the same empty shell:

```<code>@interface chronos2Tests : SenTestCase {
@private

}
@end
</code>```

In the .m file, I can write unit test methods, which names started with test. I have thought, that I must declare all member functions in the .h file? Is it possible, to write private member functions in objective c without declaring them in the .h file?

答: In Objective-C, you never have to declare methods. ObjC passes messages that are dispatched at runtime. We declare methods because it provides documentation for programmers. The compiler generates warnings in many cases when you pass messages that have no matching method, but again this is to help programmers. It is legal, and in some cases even correct.</p>

ContentLicense: CC BY-SA 3.0

Body:
I write my first simple unit tests and don't understand the magic objective c compiler. I can write unit test methods without declaring them in the test class .h file.

my test class remains the same empty shell:

@interface chronos2Tests : SenTestCase {
@private

}
@end

In the .m file, I can write unit test methods, which names started with test. I have thought, that I must declare all member functions in the .h file? Is it possible, to write private member functions in objective c without declaring them in the .h file?


问:
How can i display form success message on same { div } without refreshing the page?
How can I submit a form on same  without refreshing page? Here I'm submitting a pdf to drag and drop container and when I submit the form it's redirecting to upload.php. I need to display the successful message on the same container . I have not enough knowledge about the ajax. Kindly please help me to solve the issue

Here is the drag and drop container below:

Here is the result page (upload.php) below:

HTML Form:

```<code><form method="POST" action="upload.php" enctype="multipart/form-data">
  <input type="file" multiple name="file[]" accept="application/pdf">
      <input class="button-primary" type="submit" value="Submit">
</form>
</code>```

Upload.php file:

```<code><?php
//echo 'done';
$output = '';

    if(isset($_FILES['file']['name'][0])){
        //echo 'ok';
        foreach($_FILES['file']['name'] as $keys => $values) {

            if(move_uploaded_file($_FILES['file']['tmp_name'][$keys], 'upload/' .$values)) {

                $output .= 'Form submited succesfully';
            }
        }
    }
echo $output;
?>
</code>```

答:
You can prevent the default behaviour of the form on submit, which redirects it.
Try using this:

```<code><form id="form" method="POST" enctype="multipart/form-data">
  <input id='file' type="file" multiple name="file[]" accept="application/pdf">
  <input class="button-primary" type="submit" value="Submit">
</form>
<p id="response-text"></p>
    <script>
        $("#form").submit(function (e) {
            e.preventDefault();
            var xhttp = new XMLHttpRequest();
            var data = new FormData();
            data.append("file", document.getElementById("file").files[0]);
            xhttp.onreadystatechange = function () {
                if (this.readyState == 4 && this.status == 200) {
                    document.getElementById("response-text").innerHTML = 'Form Successfully Submitted';
                }
                else {
                    document.getElementById("response-text").innerHTML = 'Form could not be submitted';
                }
            };
            xhttp.open("post", "/upload.php", true);
            xhttp.send(data);
        });

    </script>
</code>```

Now you can display the desired message wherever you want to display. Here I have displayed on
 of id response-text

Body:
How can I submit a form on same  without refreshing page? Here I'm submitting a pdf to drag and drop container and when I submit the form it's redirecting to upload.php. I need to display the successful message on the same container . I have not enough knowledge about the ajax. Kindly please help me to solve the issue

Here is the drag and drop container below:

Here is the result page (upload.php) below:

HTML Form:

<form method="POST" action="upload.php" enctype="multipart/form-data">
  <input type="file" multiple name="file[]" accept="application/pdf">
      <input class="button-primary" type="submit" value="Submit">
</form>

Upload.php file:

<?php
//echo 'done';
$output = '';

    if(isset($_FILES['file']['name'][0])){
        //echo 'ok';
        foreach($_FILES['file']['name'] as $keys => $values) {

            if(move_uploaded_file($_FILES['file']['tmp_name'][$keys], 'upload/' .$values)) {

                $output .= 'Form submited succesfully';
            }
        }
    }
echo $output;
?>

Body:
You can prevent the default behaviour of the form on submit, which redirects it.
Try using this:

<form id="form" method="POST" enctype="multipart/form-data">
  <input id='file' type="file" multiple name="file[]" accept="application/pdf">
  <input class="button-primary" type="submit" value="Submit">
</form>
<p id="response-text"></p>
    <script>
        $("#form").submit(function (e) {
            e.preventDefault();
            var xhttp = new XMLHttpRequest();
            var data = new FormData();
            data.append("file", document.getElementById("file").files[0]);
            xhttp.onreadystatechange = function () {
                if (this.readyState == 4 && this.status == 200) {
                    document.getElementById("response-text").innerHTML = 'Form Successfully Submitted';
                }
                else {
                    document.getElementById("response-text").innerHTML = 'Form could not be submitted';
                }
            };
            xhttp.open("post", "/upload.php", true);
            xhttp.send(data);
        });

    </script>

Now you can display the desired message wherever you want to display. Here I have displayed on <p> of id response-text


问:
Seting a Curl command to run in a Zapier Webhook
I'm trying to find the way to run cURL query in Zapier webhook, but I can't seem to figure it out. How would I enter this in the Webhook?

```<code>curl 'https://api.com/graphql' -H 'Accept-Encoding: gzip, deflate, br' -H 'Content-Type: application/json' -H 'Accept: application/json' -H 'Connection: keep-alive' -H 'DNT: 1' -H 'Origin: https://api.com' -H 'access_token: <my token>' --data-binary '{"query":"{\n  booking(booking_id: \"11111\"){\n    user{\n      name\n    }\n    body\n  }\n}\n"}' --compressed
</code>```

This is the error I'm getting:

答: You need to put query in the left box under Query String Params. query is the key, the value is {\n booking(book.... You don't need quotes, either.

Body:
I'm trying to find the way to run cURL query in Zapier webhook, but I can't seem to figure it out. How would I enter this in the Webhook?

curl 'https://api.com/graphql' -H 'Accept-Encoding: gzip, deflate, br' -H 'Content-Type: application/json' -H 'Accept: application/json' -H 'Connection: keep-alive' -H 'DNT: 1' -H 'Origin: https://api.com' -H 'access_token: <my token>' --data-binary '{"query":"{\n  booking(booking_id: \"11111\"){\n    user{\n      name\n    }\n    body\n  }\n}\n"}' --compressed

This is the error I'm getting:


问:
setting class variable instead of working with redundant local variables in 'CreateView'
I have created a view class inherit from

django.views.generic.CreateView

All is working fine, but I have two times the following line of code in two different class methods:

```<code>event = get_object_or_404(Event, pk=self.kwargs['pk'])
</code>```

I have already tried to set a class variable in the init method, but all I have tried end up in error messages.

Here is my class with the redundant two lines:

```<code>class StaffCreateView(CreateView):
    model = Staff
    form_class = StaffForm

    def get_initial(self):
        """
        Returns the initial data to use for forms on this view.
        """
        initial = super().get_initial()

        event = get_object_or_404(Event, pk=self.kwargs['pk'])

        initial['country'] = event.default_country_of_staff
        initial['max_number_of_shifts'] = event.default_max_number_of_shifts_per_staff

        return initial

    def form_valid(self, form):
        event = get_object_or_404(Event, pk=self.kwargs['pk'])
        form.instance.event = event
        return super().form_valid(form)
</code>```

Can someone guide me how to do it the correct way?

答:
Finally I found the flowchart of django.views.generic.base.View in https://docs.djangoproject.com/en/2.2/ref/class-based-views/base/#django.views.generic.base.View:

setup()

dispatch()

http_method_not_allowed()

options()

According the description of the setup() method, I think this is the place to set my instance attribute self.event

So my class looks like this now:

```<code>class StaffCreateView(CreateView):
model = Staff
form_class = StaffForm

def setup(self, request, *args, **kwargs):
    super().setup(request, *args, **kwargs)
    self.event = get_object_or_404(Event, pk=self.kwargs['pk'])

def get_initial(self):
    """
    Returns the initial data to use for forms on this view.
    """
    initial = super().get_initial()

    initial['country'] = self.event.default_country_of_staff
    initial['max_number_of_shifts'] = self.event.default_max_number_of_shifts_per_staff

    return initial

def form_valid(self, form):
    form.instance.event = self.event
    return super().form_valid(form)
</code>```

Body:
I have created a view class inherit from

django.views.generic.CreateView

All is working fine, but I have two times the following line of code in two different class methods:

event = get_object_or_404(Event, pk=self.kwargs['pk'])

I have already tried to set a class variable in the init method, but all I have tried end up in error messages.

Here is my class with the redundant two lines:

class StaffCreateView(CreateView):
    model = Staff
    form_class = StaffForm

    def get_initial(self):
        """
        Returns the initial data to use for forms on this view.
        """
        initial = super().get_initial()

        event = get_object_or_404(Event, pk=self.kwargs['pk'])

        initial['country'] = event.default_country_of_staff
        initial['max_number_of_shifts'] = event.default_max_number_of_shifts_per_staff

        return initial

    def form_valid(self, form):
        event = get_object_or_404(Event, pk=self.kwargs['pk'])
        form.instance.event = event
        return super().form_valid(form)

Can someone guide me how to do it the correct way?

Body:
Finally I found the flowchart of django.views.generic.base.View in https://docs.djangoproject.com/en/2.2/ref/class-based-views/base/#django.views.generic.base.View:

setup()

dispatch()

http_method_not_allowed()

options()

According the description of the setup() method, I think this is the place to set my instance attribute self.event

So my class looks like this now:

class StaffCreateView(CreateView):
model = Staff
form_class = StaffForm

def setup(self, request, *args, **kwargs):
    super().setup(request, *args, **kwargs)
    self.event = get_object_or_404(Event, pk=self.kwargs['pk'])

def get_initial(self):
    """
    Returns the initial data to use for forms on this view.
    """
    initial = super().get_initial()

    initial['country'] = self.event.default_country_of_staff
    initial['max_number_of_shifts'] = self.event.default_max_number_of_shifts_per_staff

    return initial

def form_valid(self, form):
    form.instance.event = self.event
    return super().form_valid(form)


问:
Visual Studio For Mac Debugging Unit Tests
I just downloaded VS 2019 for Mac.  Console projects debugging works fine hitting break points. If I try to debug a MSTest or NUnit test project the break points are ignored with no error message.

I have tried changing the options, I am in debug mode, I have tried restarting, and creating new projects. I have downloaded the MSTest.TestFramework, and MSTest.TestAdapter from nuget. None of these have worked.

Any ideas on how to resolve this?

答:
Go to "Menu" -> "View" - "Test'.
Find your test... right click on it... and "Debug test"


问:
Protecting an specific WordPress page with .htaccess
I have a specific page on my WordPress installation (it's an actual Page in WordPress, just with Pretty URLs) and I want to password-protect it with an .htaccess file provided to me.

For example, the page is http://www.myawesomewebsite.com/members . I want only some users to access it, and their user and password are stored in an .htpasswd file.

The .htaccess file the client sent to me is

```<code>AuthUserFile /put the path to the password file here
AuthGroupFile /dev/null
AuthName RESTRICTED
AuthType Basic

<Limit GET POST>
require valid-user
</Limit>
</code>```

I need to use this parameters to protect this WordPress page. I'm going crazy and my searches are leading to nowhere. Any guesses?

答: Wordpress allows you to protect the pages/posts using password ( and it's rather easyer to go this route than with htaccess ) : go to wp-admin, edit the page/post you like to keep private but allow access to some users too, and right under the "preview changes" button you'll see "Status: Published Edit" and beneth it "Visibility: Public Edit" click the visibility edit, select the Password Protected radiobox ( or private for that matter ) enter a password and hit Ok . You should be good to go .</p>

Body:
I have a specific page on my WordPress installation (it's an actual Page in WordPress, just with Pretty URLs) and I want to password-protect it with an .htaccess file provided to me.

For example, the page is http://www.myawesomewebsite.com/members . I want only some users to access it, and their user and password are stored in an .htpasswd file.

The .htaccess file the client sent to me is

AuthUserFile /put the path to the password file here
AuthGroupFile /dev/null
AuthName RESTRICTED
AuthType Basic

<Limit GET POST>
require valid-user
</Limit>

I need to use this parameters to protect this WordPress page. I'm going crazy and my searches are leading to nowhere. Any guesses?


问:
How to inject data-model mock into spring controller?
In my unit tests, I need to mock a data-model instance in a spring @Controller, else the return value of the @RequestMapping method gets wrong.

To do this I tried the following:

Create a User mock, which calls user.login() and needs to return "true"

Inject mock object in the LoginController

Stub the login method to return true

Perform POST /Login with MockMVC from spring test

verify that mockUser.login got called

Here is the controller method:

```<code>@RequestMapping(value = "/Login", method = RequestMethod.POST)
  public String updateUI(Locale locale, Model model, @RequestParam("username") String username,
      @RequestParam("hashedPW") String hashedPW, HttpServletRequest request) {
    model.addAttribute("username", username);
    user = new User(username, username, hashedPW.getBytes(), LoginHandler.getInstance());

    boolean loginResult = user.login();
    if(loginResult == true) {
      return "profile";
    }
    String output = "Failed login (" + username + ") requested, locale = " + locale;
    log(output);
    return "home";
  }
</code>```

and my initialization of mock objects with injection:

```<code>@Mock
  private User mockUser;

  @InjectMocks
  private LoginController injectedLoginController;

  @Before
  public void setup() throws ServletException {
    MockitoAnnotations.initMocks(this);
    mvc = MockMvcBuilders.standaloneSetup(injectedLoginController).build();
    LOGFILE = new File("logs/general.log");
  }
</code>```

and finally the unit test:

```<code>@Test
  public void testLoginSuccess() throws Exception {
    String username = "Stefan";
    byte[] hashedPW = "".getBytes();
    when(mockUser.login()).thenReturn(true);
    ResultActions ra = mvc
        .perform(post("/Login").param("username", username).param("hashedPW", hashedPW.toString()))
        .andExpect(status().isOk());

    verify(mockUser).login();
  }
</code>```

All together I expected the User object that is handled by the controller to be of mockUser type instead of User, and the login() method to get called once (accordingly) and return "true".

But all I get is
"Wanted but not invoked: mockUser.login()
 Actually, there was zero interaction with this mock."

I appreciate any suggestions to solve my problem since I am working on this for quite some time now and I don't seem to get the trick.

答:
1) This seems to be an IT test.. you should not force any injection.. spring does that:

```<code>@InjectMocks
private LoginController injectedLoginController;
</code>```

2) You need to spy on your controller:

```<code>@SpyBean
private LoginController injectedLoginController;
</code>```

3) You need to move the creation of the User to a package level method inside the controller:

```<code>user = createUser(username, username, hashedPW.getBytes(), LoginHandler.getInstance());

...

User createUser(...){
   return new User(username, username, hashedPW.getBytes(), LoginHandler.getInstance());
}
</code>```

4) Make that method return a mocked User:

```<code>  doReturn(mockUser).when(injectedLoginController).createUser(...);
  when(mockUser.login()).thenReturn(true);
</code>```

Body:
In my unit tests, I need to mock a data-model instance in a spring @Controller, else the return value of the @RequestMapping method gets wrong.

To do this I tried the following:

Create a User mock, which calls user.login() and needs to return "true"

Inject mock object in the LoginController

Stub the login method to return true

Perform POST /Login with MockMVC from spring test

verify that mockUser.login got called

Here is the controller method:

@RequestMapping(value = "/Login", method = RequestMethod.POST)
  public String updateUI(Locale locale, Model model, @RequestParam("username") String username,
      @RequestParam("hashedPW") String hashedPW, HttpServletRequest request) {
    model.addAttribute("username", username);
    user = new User(username, username, hashedPW.getBytes(), LoginHandler.getInstance());

    boolean loginResult = user.login();
    if(loginResult == true) {
      return "profile";
    }
    String output = "Failed login (" + username + ") requested, locale = " + locale;
    log(output);
    return "home";
  }

and my initialization of mock objects with injection:

@Mock
  private User mockUser;

  @InjectMocks
  private LoginController injectedLoginController;

  @Before
  public void setup() throws ServletException {
    MockitoAnnotations.initMocks(this);
    mvc = MockMvcBuilders.standaloneSetup(injectedLoginController).build();
    LOGFILE = new File("logs/general.log");
  }

and finally the unit test:

@Test
  public void testLoginSuccess() throws Exception {
    String username = "Stefan";
    byte[] hashedPW = "".getBytes();
    when(mockUser.login()).thenReturn(true);
    ResultActions ra = mvc
        .perform(post("/Login").param("username", username).param("hashedPW", hashedPW.toString()))
        .andExpect(status().isOk());

    verify(mockUser).login();
  }

All together I expected the User object that is handled by the controller to be of mockUser type instead of User, and the login() method to get called once (accordingly) and return "true".

But all I get is
"Wanted but not invoked: mockUser.login()
 Actually, there was zero interaction with this mock."

I appreciate any suggestions to solve my problem since I am working on this for quite some time now and I don't seem to get the trick.

Body:
1) This seems to be an IT test.. you should not force any injection.. spring does that:

@InjectMocks
private LoginController injectedLoginController;

2) You need to spy on your controller:

@SpyBean
private LoginController injectedLoginController;

3) You need to move the creation of the User to a package level method inside the controller:

user = createUser(username, username, hashedPW.getBytes(), LoginHandler.getInstance());

...

User createUser(...){
   return new User(username, username, hashedPW.getBytes(), LoginHandler.getInstance());
}

4) Make that method return a mocked User:

  doReturn(mockUser).when(injectedLoginController).createUser(...);
  when(mockUser.login()).thenReturn(true);


问:
EMR DAG terminates before all steps are completed
I am using the EMR CreateJobFlow, AddSteps,StepSensor and TerminateJobFlow operators in my DAG to start up an EMR cluster, add steps (2 spark apps, and dist-cp), and terminate when all steps are completed or 1 fails. I am able to do this when I have a 2 step DAG (1st is Spark app, 2nd is dist-cp), however, when I have 2 spark apps, the cluster successfully runs the 1st step, and terminates without moving on to the 2nd and 3rd steps.

Through some digging, I can see that Airflow "pokes" steps to see if they are still running. In this instance, it seems to think that it's "Successful" only when 1 step is finished.

My spark apps are fairly simple. The first creates and writes a dataframe to local HDFS. The 2nd reads the data from HDFS and joins to another data set and writes back to HDFS. The third step is s3-dist-cp to copy the data from HDFS to s3. All 3 steps can be successfully run within Spark-Shell interactively, or as Spark-Submit jobs. I have also cloned the EMR cluster myself (without airflow) and saw all steps succeed without any errors, so EMR and Spark are not the issue here.

The DAG is below

    from datetime import timedelta

    import airflow
    from airflow import DAG
    from airflow.contrib.operators.emr_create_job_flow_operator \
        import EmrCreateJobFlowOperator
    from airflow.contrib.operators.emr_add_steps_operator \
        import EmrAddStepsOperator
    from airflow.contrib.sensors.emr_step_sensor import EmrStepSensor
    from airflow.contrib.operators.emr_terminate_job_flow_operator \
        import EmrTerminateJobFlowOperator

    DEFAULT_ARGS = {
        'owner': 'airflow',
        'depends_on_past': False,
        'start_date': airflow.utils.dates.days_ago(2)
    }

    SPARK_TEST_STEPS = [
        {
            'Name': 'monthly_agg',
            'ActionOnFailure': 'CONTINUE',
            'HadoopJarStep': {
                'Jar': 'command-runner.jar',
                'Args': ['spark-submit',
                          '--deploy-mode',
                           'cluster',
                          '--class' ,
                          'AggApp',
                          's3://jar1.jar' ]
                            }
        },
        {
            'Name': 'monthly_agg2',
            'ActionOnFailure': 'CONTINUE',
            'HadoopJarStep': {
                'Jar': 'command-runner.jar',
                'Args': ['spark-submit',
                          '--deploy-mode',
                           'cluster',
                          '--class' ,
                          'SimpleApp',
                          's3:/jar2.jar' ]
                            }
        },

        {
            'Name': 'copy-data',
            'ActionOnFailure': 'CONTINUE',
            'HadoopJarStep': {
                'Jar': 'command-runner.jar',
                'Args': ['s3-dist-cp',
                          '--src',
                          '/tempo',
                          '--dest',
                           's3://mydata/'
                        ]
                            }
        }
    ]

    JOB_FLOW_OVERRIDES = {
    'Instances': {'Ec2SubnetId': 'subnet-mysubnetid',
        'InstanceGroups': [
            {
                'Name': 'Master nodes',
                'Market': 'ON_DEMAND',
                'InstanceRole': 'MASTER',
                'InstanceType': 'r4.2xlarge',
                'InstanceCount': 1
            },
            {
                'Name': 'Slave nodes',
                'Market': 'ON_DEMAND',
                'InstanceRole': 'CORE',
                'InstanceType': 'r4.2xlarge',
                'InstanceCount': 8,
                'EbsConfiguration': {'EbsBlockDeviceConfigs':[{'VolumeSpecification':{'SizeInGB':128,'VolumeType':'gp2'},'VolumesPerInstance':1}],'EbsOptimized':True}
            }
        ]},
        'Name':'airflow-monthly_agg_custom',
        'Configurations': [
        {
        'Classification':'spark-defaults','Properties':
            {'spark.sql.crossJoin.enabled':'true',
            'spark.serializer':'org.apache.spark.serializer.KryoSerializer',
            'spark.hadoop.mapreduce.fileoutputcommitter.algorithm.version':'2',
            "maximizeResourceAllocation":"true"},
        'Configurations':[]
        },
        {
        'Classification':'spark-hive-site','Properties':
        {'hive.metastore.client.factory.class':'com.amazonaws.glue.catalog.metastore.AWSGlueDataCatalogHiveClientFactory'},
        'Configurations':[]
        }
        ]}

    dag = DAG(
        'monthly_agg_custom',
        default_args=DEFAULT_ARGS,
        dagrun_timeout=timedelta(hours=4),
        schedule_interval='@once'
    )

    cluster_creator = EmrCreateJobFlowOperator(
        task_id='create_job_flow',
        job_flow_overrides=JOB_FLOW_OVERRIDES,
        aws_conn_id='aws_default',
        emr_conn_id='emr_default',
        dag=dag
    )

    step_adder = EmrAddStepsOperator(
        task_id='add_steps',
        job_flow_id="{{ task_instance.xcom_pull('create_job_flow', key='return_value') }}",
        aws_conn_id='aws_default',
        steps=SPARK_TEST_STEPS,
        dag=dag
    )

    step_checker = EmrStepSensor(
        task_id='watch_step',
        job_flow_id="{{ task_instance.xcom_pull('create_job_flow', key='return_value') }}",
        step_id="{{ task_instance.xcom_pull('add_steps', key='return_value')[0] }}",
        aws_conn_id='aws_default',
        dag=dag
    )

    cluster_remover = EmrTerminateJobFlowOperator(
        task_id='remove_cluster',
        job_flow_id="{{ task_instance.xcom_pull('create_job_flow', key='return_value') }}",
        aws_conn_id='aws_default',
        dag=dag
    )

    cluster_creator.set_downstream(step_adder)
    step_adder.set_downstream(step_checker)
    step_checker.set_downstream(cluster_remover)
```

答:
The problem is that you are feeding EmrStepSensor all steps in as one stepadder, so as soon as one finishes, it  terminates the cluster.

The solution is to separate all steps and give the last step'id to the EmrStepSensor. Alternatively, you can only the last step with its separate step adder (step_adder_actual_step) from others and provided it to EmrStepSensor

```<code>step_adder_pre_step = EmrAddStepsOperator(
    task_id='pre_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    steps=pre_step,
    dag=dag
)

step_adder_actual_step = EmrAddStepsOperator(
    task_id='actual_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    steps=actual_step,
    dag=dag
)

step_checker = EmrStepSensor(
    task_id='watch_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    step_id="{{ task_instance.xcom_pull('actual_step', key='return_value')[0] }}",
    aws_conn_id='aws_default',
    dag=dag
)

cluster_remover = EmrTerminateJobFlowOperator(
    task_id='remove_cluster',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    dag=dag
)

cluster_creator >> step_adder_pre_step >> step_adder_actual_step >> step_checker >> cluster_remover
</code>```

Body:
The problem is that you are feeding EmrStepSensor all steps in as one stepadder, so as soon as one finishes, it  terminates the cluster.

The solution is to separate all steps and give the last step'id to the EmrStepSensor. Alternatively, you can only the last step with its separate step adder (step_adder_actual_step) from others and provided it to EmrStepSensor

step_adder_pre_step = EmrAddStepsOperator(
    task_id='pre_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    steps=pre_step,
    dag=dag
)

step_adder_actual_step = EmrAddStepsOperator(
    task_id='actual_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    steps=actual_step,
    dag=dag
)

step_checker = EmrStepSensor(
    task_id='watch_step',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    step_id="{{ task_instance.xcom_pull('actual_step', key='return_value')[0] }}",
    aws_conn_id='aws_default',
    dag=dag
)

cluster_remover = EmrTerminateJobFlowOperator(
    task_id='remove_cluster',
    job_flow_id="{{ task_instance.xcom_pull('create_job_flow2', key='return_value') }}",
    aws_conn_id='aws_default',
    dag=dag
)

cluster_creator >> step_adder_pre_step >> step_adder_actual_step >> step_checker >> cluster_remover


问:
Android: AnimatedVectorDrawable Loop
I'm playing around with AnimatedVectorDrawables using https://shapeshifter.design/ The exported file I got is below. My research Tells me that in order to loop an animations i should add android:repeatCount="infinite" and android:repeatMode="restart" to the objectAnimator.

Adding this to the objectAnimator only repeats one of these items out of series. How would I loop the entire series of animations? I want the animation to start on load and repeat.

Animation XML

```<code><animated-vector
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:aapt="http://schemas.android.com/aapt">
    <aapt:attr name="android:drawable">
        <vector
            xmlns:android="http://schemas.android.com/apk/res/android"
            android:width="50dp"
            android:height="50dp"
            android:viewportWidth="50"
            android:viewportHeight="50">
            <path
                android:name="_x34_"
                android:pathData="M 25 12.3 L 39.7 37.7 L 10.3 37.7 Z"
                android:fillColor="#ffffff"
                android:strokeColor="#000000"
                android:strokeWidth="1"
                android:strokeLineCap="round"
                android:strokeLineJoin="round"
                android:strokeMiterLimit="10"/>
        </vector>
    </aapt:attr>
    <target android:name="_x34_">
        <aapt:attr name="android:animation">
            <set xmlns:android="http://schemas.android.com/apk/res/android">
                <objectAnimator
                    android:propertyName="pathData"
                    android:duration="1000"
                    android:valueFrom="M 25 12.3 L 39.7 37.7 L 10.3 37.7 L 17.397 25.437 Z"
                    android:valueTo="M 10 10 L 40 10 L 40 40 L 10 40 Z"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/overshoot_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="1000"
                    android:duration="1000"
                    android:valueFrom="M 40 10 L 25.581 10 L 10 10 L 10 40 L 25.349 40 L 40 40 L 40 10"
                    android:valueTo="M 36.3 18.7 L 25 10.4 L 13.7 18.7 L 12.8 31.5 L 25 39.6 L 37.2 31.5 L 36.3 18.7"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="2000"
                    android:duration="1000"
                    android:valueFrom="M 36.3 18.7 L 25 10.4 L 13.7 18.7 L 12.8 31.5 L 25 39.6 L 37.2 31.5 Z"
                    android:valueTo="M 25 10.2 L 12.2 17.6 L 12.2 32.4 L 25 39.8 L 37.8 32.4 L 37.8 17.6 Z"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/overshoot_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="3000"
                    android:duration="1000"
                    android:valueFrom="M 31.365 13.88 L 25 10.2 L 18.268 14.092 L 12.2 17.6 L 12.2 25.465 L 12.2 32.4 L 25 39.8 L 37.8 32.4 L 37.8 25.581 L 37.8 17.6 L 31.365 13.88"
                    android:valueTo="M 33.7 13 L 25 10.2 L 16.3 13 L 10.9 20.4 L 10.9 29.6 L 16.3 37 L 25 39.8 L 33.7 37 L 39.1 29.6 L 39.1 20.4 L 33.7 13"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/decelerate_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="4000"
                    android:duration="1000"
                    android:valueFrom="M 39.1 20.4 L 33.7 13 L 25 10.2 L 16.3 13 L 10.9 20.4 L 10.9 29.6 L 16.3 37 L 25 39.8 L 33.7 37 L 39.1 29.6 L 39.1 20.4"
                    android:valueTo="M 39.7 20 L 32.199 16.173 L 25 12.5 L 17.885 16.13 L 10.3 20 L 10 31 L 16.994 34.031 L 25 37.5 L 32.948 34.056 L 40 31 L 39.7 20"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="5000"
                    android:duration="1000"
                    android:valueFrom="M 10.3 20 L 25 12.5 L 39.7 20 L 40 31 L 25 37.5 L 10 31 L 10.3 20"
                    android:valueTo="M 17.995 24.403 L 25 12.3 L 32.23 24.792 L 39.7 37.7 L 25.581 37.7 L 10.3 37.7 L 17.995 24.403"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
            </set>
        </aapt:attr>
    </target>
</animated-vector>
</code>```

My java code for implementing the Animation is as follows:

```<code>final ImageView animationView = (ImageView) findViewById(R.id.animationView);
final AnimatedVectorDrawable drawable = (AnimatedVectorDrawable) getDrawable(R.drawable.avd_dice);
animationView.setImageDrawable(drawable);
drawable.start();
</code>```

答:
Using @Feryal Sharifzadeh great answer as a base, here's a Kotlin ext function for setting and looping a AVD. </p>

```<code>internal fun ImageView.applyLoopingAnimatedVectorDrawable(@DrawableRes avdResId: Int) {
    val animated = AnimatedVectorDrawableCompat.create(context, avdResId)
    animated?.registerAnimationCallback(object : Animatable2Compat.AnimationCallback() {
        override fun onAnimationEnd(drawable: Drawable?) {
            this@applyLoopingAnimatedVectorDrawable.post { animated.start() }
        }
    })
    this.setImageDrawable(animated)
    animated?.start()
}
</code>```

Title: Android: AnimatedVectorDrawable Loop

Body:
I'm playing around with AnimatedVectorDrawables using https://shapeshifter.design/ The exported file I got is below. My research Tells me that in order to loop an animations i should add android:repeatCount="infinite" and android:repeatMode="restart" to the objectAnimator.

Adding this to the objectAnimator only repeats one of these items out of series. How would I loop the entire series of animations? I want the animation to start on load and repeat.

Animation XML

<animated-vector
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:aapt="http://schemas.android.com/aapt">
    <aapt:attr name="android:drawable">
        <vector
            xmlns:android="http://schemas.android.com/apk/res/android"
            android:width="50dp"
            android:height="50dp"
            android:viewportWidth="50"
            android:viewportHeight="50">
            <path
                android:name="_x34_"
                android:pathData="M 25 12.3 L 39.7 37.7 L 10.3 37.7 Z"
                android:fillColor="#ffffff"
                android:strokeColor="#000000"
                android:strokeWidth="1"
                android:strokeLineCap="round"
                android:strokeLineJoin="round"
                android:strokeMiterLimit="10"/>
        </vector>
    </aapt:attr>
    <target android:name="_x34_">
        <aapt:attr name="android:animation">
            <set xmlns:android="http://schemas.android.com/apk/res/android">
                <objectAnimator
                    android:propertyName="pathData"
                    android:duration="1000"
                    android:valueFrom="M 25 12.3 L 39.7 37.7 L 10.3 37.7 L 17.397 25.437 Z"
                    android:valueTo="M 10 10 L 40 10 L 40 40 L 10 40 Z"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/overshoot_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="1000"
                    android:duration="1000"
                    android:valueFrom="M 40 10 L 25.581 10 L 10 10 L 10 40 L 25.349 40 L 40 40 L 40 10"
                    android:valueTo="M 36.3 18.7 L 25 10.4 L 13.7 18.7 L 12.8 31.5 L 25 39.6 L 37.2 31.5 L 36.3 18.7"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="2000"
                    android:duration="1000"
                    android:valueFrom="M 36.3 18.7 L 25 10.4 L 13.7 18.7 L 12.8 31.5 L 25 39.6 L 37.2 31.5 Z"
                    android:valueTo="M 25 10.2 L 12.2 17.6 L 12.2 32.4 L 25 39.8 L 37.8 32.4 L 37.8 17.6 Z"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/overshoot_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="3000"
                    android:duration="1000"
                    android:valueFrom="M 31.365 13.88 L 25 10.2 L 18.268 14.092 L 12.2 17.6 L 12.2 25.465 L 12.2 32.4 L 25 39.8 L 37.8 32.4 L 37.8 25.581 L 37.8 17.6 L 31.365 13.88"
                    android:valueTo="M 33.7 13 L 25 10.2 L 16.3 13 L 10.9 20.4 L 10.9 29.6 L 16.3 37 L 25 39.8 L 33.7 37 L 39.1 29.6 L 39.1 20.4 L 33.7 13"
                    android:valueType="pathType"
                    android:interpolator="@android:anim/decelerate_interpolator"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="4000"
                    android:duration="1000"
                    android:valueFrom="M 39.1 20.4 L 33.7 13 L 25 10.2 L 16.3 13 L 10.9 20.4 L 10.9 29.6 L 16.3 37 L 25 39.8 L 33.7 37 L 39.1 29.6 L 39.1 20.4"
                    android:valueTo="M 39.7 20 L 32.199 16.173 L 25 12.5 L 17.885 16.13 L 10.3 20 L 10 31 L 16.994 34.031 L 25 37.5 L 32.948 34.056 L 40 31 L 39.7 20"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
                <objectAnimator
                    android:propertyName="pathData"
                    android:startOffset="5000"
                    android:duration="1000"
                    android:valueFrom="M 10.3 20 L 25 12.5 L 39.7 20 L 40 31 L 25 37.5 L 10 31 L 10.3 20"
                    android:valueTo="M 17.995 24.403 L 25 12.3 L 32.23 24.792 L 39.7 37.7 L 25.581 37.7 L 10.3 37.7 L 17.995 24.403"
                    android:valueType="pathType"
                    android:interpolator="@android:interpolator/fast_out_slow_in"/>
            </set>
        </aapt:attr>
    </target>
</animated-vector>

My java code for implementing the Animation is as follows:

final ImageView animationView = (ImageView) findViewById(R.id.animationView);
final AnimatedVectorDrawable drawable = (AnimatedVectorDrawable) getDrawable(R.drawable.avd_dice);
animationView.setImageDrawable(drawable);
drawable.start();

Body:
Using @Feryal Sharifzadeh great answer as a base, here's a Kotlin ext function for setting and looping a AVD.

internal fun ImageView.applyLoopingAnimatedVectorDrawable(@DrawableRes avdResId: Int) {
    val animated = AnimatedVectorDrawableCompat.create(context, avdResId)
    animated?.registerAnimationCallback(object : Animatable2Compat.AnimationCallback() {
        override fun onAnimationEnd(drawable: Drawable?) {
            this@applyLoopingAnimatedVectorDrawable.post { animated.start() }
        }
    })
    this.setImageDrawable(animated)
    animated?.start()
}


问:
pass kwargs and default values to ordered list
Using python 2.7, I have been researching into using keyword arguments to pass a function that inserts a new tuple into a list.

My goal: have a function that takes one required argument, and n number of arguments that then get inserted into a tuple at specific positions and have a default value if nothing was passed.

Here is what I have so far:

```<code>def add_tagging_log_row(key, **time_stamp):
    tagging_log_rows.insert(len(tagging_log_rows), (key, time_stamp.get('is_processed'), time_stamp.get('is_processed')))

add_tagging_log_row('zzz', is_processed=datetime.datetime.now(), is_audited=datetime.datetime.now())
</code>```

Here is a sample of tagging_low_rows list I am building with all values in the tuple populated:

```<code>[('key1', datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now()), ('key2', datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now())]
</code>```

here is the order of the items in each tuple in the list:

```<code>key | is_processed | is_archived | is_error | is_audited
</code>```

The problem is when calling the function add_tagging_log_row(), I will always pass a 'key' but might or might not pass the other timestamp fields to the tuple when it is inserted into the list. I need these fields to be empty strings ('').

Is using **kwargs the right way to approach this problem?

答:
Yes, using kwargs works. You would need some exception handling inside your function though. kwargs passed in as a dictionary. You can check if a given timestamp exists in the dictionary and use an empty string if it doesn't. Try doing something like this inside the function:

```<code>timestamps_order = ['is_processed', 'is_archived', 'is_error', 'is_audited']
required_tuple = tuple([key] + [time_stamp[k] if k in time_stamp else "" for k in timestamps_order])
</code>```

On a side note - please consider switching to Python 3. Python 2.7 is at the end of life and won't receive any future support. Most libraries have stopped supporting it.

Body:
Using python 2.7, I have been researching into using keyword arguments to pass a function that inserts a new tuple into a list.

My goal: have a function that takes one required argument, and n number of arguments that then get inserted into a tuple at specific positions and have a default value if nothing was passed.

Here is what I have so far:

def add_tagging_log_row(key, **time_stamp):
    tagging_log_rows.insert(len(tagging_log_rows), (key, time_stamp.get('is_processed'), time_stamp.get('is_processed')))

add_tagging_log_row('zzz', is_processed=datetime.datetime.now(), is_audited=datetime.datetime.now())

Here is a sample of tagging_low_rows list I am building with all values in the tuple populated:

[('key1', datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now()), ('key2', datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now(), datetime.datetime.now())]

here is the order of the items in each tuple in the list:

key | is_processed | is_archived | is_error | is_audited

The problem is when calling the function add_tagging_log_row(), I will always pass a 'key' but might or might not pass the other timestamp fields to the tuple when it is inserted into the list. I need these fields to be empty strings ('').

Is using **kwargs the right way to approach this problem?

Body:
Yes, using kwargs works. You would need some exception handling inside your function though. kwargs passed in as a dictionary. You can check if a given timestamp exists in the dictionary and use an empty string if it doesn't. Try doing something like this inside the function:

timestamps_order = ['is_processed', 'is_archived', 'is_error', 'is_audited']
required_tuple = tuple([key] + [time_stamp[k] if k in time_stamp else "" for k in timestamps_order])

On a side note - please consider switching to Python 3. Python 2.7 is at the end of life and won't receive any future support. Most libraries have stopped supporting it.


问:
Remove zeros from a matrix
I have a matrix with large rows and columns as follows:

```<code>A = 0    0  0  0
    0    0  0  0
    0    0  0  0
    2000 11 16 -0.74
    0    0  0  0
    0    0  0  0
    2000 12 26 -0.84
    0    0  0  0
    0    0  0  0
</code>```

I need to remove all the zeros from the matrix to get output like,

```<code>B = 2000 11 16 -0.74
    2000 12 26 -0.84
</code>```

I have tried an available solution over here like,

```<code>B = A(A~=0)
</code>```

It removes zeros but gives output like,

```<code>2000
2000
11
12
-0.74
-0.84
</code>```

How to get the desired output?

Title: Remove zeros from a matrix

Body:
I have a matrix with large rows and columns as follows:

A = 0    0  0  0
    0    0  0  0
    0    0  0  0
    2000 11 16 -0.74
    0    0  0  0
    0    0  0  0
    2000 12 26 -0.84
    0    0  0  0
    0    0  0  0

I need to remove all the zeros from the matrix to get output like,

B = 2000 11 16 -0.74
    2000 12 26 -0.84

I have tried an available solution over here like,

B = A(A~=0)

It removes zeros but gives output like,

2000
2000
11
12
-0.74
-0.84

How to get the desired output?

Body:
assuming A is a two dimensional matrix

A(any(A,2),:)

will do.

Example:

>> A=[rand(2,3); zeros(3); rand(1,3)]
A =

   0.13878   0.44315   0.25832
   0.01879   0.93844   0.57537
   0.00000   0.00000   0.00000
   0.00000   0.00000   0.00000
   0.00000   0.00000   0.00000
   0.50581   0.37870   0.56563

>> A(any(A,2),:)
ans =

   0.138776   0.443152   0.258325
   0.018794   0.938439   0.575371
   0.505809   0.378696   0.565632


问:
Can a Spring Boot standalone application integrated with Camunda consume JMS messages from JbossFuse?
I have a activemq:queue inQueue in my JbossFuse. How do I consume those JMS messages which are enqueued so that my process instance is triggered in the Spring boot application integrated with Camunda ? Any link to references or samples would be helpful ?

Currently I am able to consume messages from activemq but I am not sure how to consume the messages from Jboss Fuse ActiveMQ ?

```<code>@Component
public class ActiveMQConsumer {

@Autowired
CamelContext camelContext;
@Autowired
ProducerTemplate producerTemplate;

@SuppressWarnings("unchecked")
@JmsListener(destination = "inQueue")
public void consumeMessage(JSONObject employeeRecord) throws Exception {

    if (employeeRecord instanceof JSONObject) {
        HashMap<String, Object> employeeRecordMap = (HashMap<String, Object>) employeeRecord.toMap();
        Exchange exchange = ExchangeBuilder.anExchange(camelContext).withBody(employeeRecordMap).build();
        HashMap<String, Object> employeeDetails = (HashMap<String, Object>) employeeRecordMap.get("employeeDetails");
        exchange.setProperty("CamundaBpmBusinessKey", employeeDetails.get("employeeADId"));
        producerTemplate.send("camunda-bpm:start?processDefinitionKey=camunda-camel-activeMQ", exchange);
    }
    }
}
</code>```

application.properties

```<code># activeMQ config
spring.activemq.broker-url=tcp://localhost:61616
spring.activemq.user=admin
spring.activemq.password=admin
</code>```

Expected to consume messages from JbossFuse.

答:
I would recommend using the maven archetype io.fabric8.archetypes spring-boot-camel-amq-archetype version 2.2.197.  This can be found:

```<code>Spring Boot example running a Camel route connecting to ActiveMQ
http://repo1.maven.org/maven2/
</code>```

This will get you a nice sample project that has all of the Camel and Spring dependencies and some nice samples.

Body:
I have a activemq:queue inQueue in my JbossFuse. How do I consume those JMS messages which are enqueued so that my process instance is triggered in the Spring boot application integrated with Camunda ? Any link to references or samples would be helpful ?

Currently I am able to consume messages from activemq but I am not sure how to consume the messages from Jboss Fuse ActiveMQ ?

@Component
public class ActiveMQConsumer {

@Autowired
CamelContext camelContext;
@Autowired
ProducerTemplate producerTemplate;

@SuppressWarnings("unchecked")
@JmsListener(destination = "inQueue")
public void consumeMessage(JSONObject employeeRecord) throws Exception {

    if (employeeRecord instanceof JSONObject) {
        HashMap<String, Object> employeeRecordMap = (HashMap<String, Object>) employeeRecord.toMap();
        Exchange exchange = ExchangeBuilder.anExchange(camelContext).withBody(employeeRecordMap).build();
        HashMap<String, Object> employeeDetails = (HashMap<String, Object>) employeeRecordMap.get("employeeDetails");
        exchange.setProperty("CamundaBpmBusinessKey", employeeDetails.get("employeeADId"));
        producerTemplate.send("camunda-bpm:start?processDefinitionKey=camunda-camel-activeMQ", exchange);
    }
    }
}

application.properties

# activeMQ config
spring.activemq.broker-url=tcp://localhost:61616
spring.activemq.user=admin
spring.activemq.password=admin

Expected to consume messages from JbossFuse.

Body:
I would recommend using the maven archetype io.fabric8.archetypes spring-boot-camel-amq-archetype version 2.2.197.  This can be found:

Spring Boot example running a Camel route connecting to ActiveMQ
http://repo1.maven.org/maven2/

This will get you a nice sample project that has all of the Camel and Spring dependencies and some nice samples.


问:
How do I play Audio in Ionic Angular?
I am aware of the NativeAudio solution, but I was wondering if it's possible to do this completely through Angular.

So far I have something but it's not really working:

```<code>import { Injectable } from '@angular/core'

@Injectable({
  providedIn: 'root',
})
export class AudioService {

  audio: HTMLAudioElement

  constructor() {
    this.audio = new Audio()
  }

  playScan = async () => {
    this.audio.src = './sound4_selfservice_scan_item.wav'
    this.audio.load()
    await this.playAudio()
  }

  playIssue = async () => {
    this.audio.src = './sound3_checkin_denied.wav'
    await this.playAudio()
  }

  playAudio = () => this.audio.play()
}
</code>```

and in my component:

```<code>@Component({
  selector: 'scan-retail-items',
  template: `
      <div class="app-container scan-item-component {{mode}} {{scanClass}}">
          <main-navigation [member]="handOffMember"
                           (onBackPressed)="onBackPressed($event)"></main-navigation>
          <div class="main-container -expanded">
                              <ion-button
                                      color="secondary"
                                      *virtualItem="let item"
                                      (click)="clickTestButton(item.upc)">{{item.name}}
                              </ion-button>
                          </ion-virtual-scroll>
                      </ion-content>
                  </div>
              </main-body>
              <status-icon mode={{mode}}></status-icon>
          </div>
      </div>
  `,
  styleUrls: ['./scan_retail_items.component.scss'],
})

export class ScanRetailItemsComponent implements OnInit, OnDestroy {

  constructor(private audio: AudioService) {
  }

  ngOnInit(): void {
  }

  clickTestButton = async (upc: string) => {
    console.log('Test Product Scan: ' + upc)
    this.addItemByUPC({ scanData: upc })
    await this.audio.playScan()
  }
</code>```

Clicking on the button calls clickTestButton and it should theoretically play the sound, but it doesn't seem like it's doing it. Is there anything I'm doing wrong until I move on to Native Audio?

答:
If you want to play audio using an HTML element you should first add it to the body of your html.
If you want a full typescript solution, you can follow the most voted answer on this other stackoverflow question: Play sound in Angular 4

A very easy way to test this. Create an empty index.html file in a folder. Put a WAV file named audio.wav in the same folder. Now open index.html in the browser. Then open DevTools and run this script:

```<code>let audio = new Audio();
audio.src = "./audio.wav";
audio.load();
audio.play();
</code>```

your WAV file should now be correctly reproduced

Title: How do I play Audio in Ionic Angular?

Body:
I am aware of the NativeAudio solution, but I was wondering if it's possible to do this completely through Angular.

So far I have something but it's not really working:

import { Injectable } from '@angular/core'

@Injectable({
  providedIn: 'root',
})
export class AudioService {

  audio: HTMLAudioElement

  constructor() {
    this.audio = new Audio()
  }

  playScan = async () => {
    this.audio.src = './sound4_selfservice_scan_item.wav'
    this.audio.load()
    await this.playAudio()
  }

  playIssue = async () => {
    this.audio.src = './sound3_checkin_denied.wav'
    await this.playAudio()
  }

  playAudio = () => this.audio.play()
}

and in my component:

@Component({
  selector: 'scan-retail-items',
  template: `

                              <ion-button
                                      color="secondary"
                                      *virtualItem="let item"
                                      (click)="clickTestButton(item.upc)">{{item.name}}
                              </ion-button>
                          </ion-virtual-scroll>
                      </ion-content>

              <status-icon mode={{mode}}></status-icon>

  `,
  styleUrls: ['./scan_retail_items.component.scss'],
})

export class ScanRetailItemsComponent implements OnInit, OnDestroy {

  constructor(private audio: AudioService) {
  }

  ngOnInit(): void {
  }

  clickTestButton = async (upc: string) => {
    console.log('Test Product Scan: ' + upc)
    this.addItemByUPC({ scanData: upc })
    await this.audio.playScan()
  }

Clicking on the button calls clickTestButton and it should theoretically play the sound, but it doesn't seem like it's doing it. Is there anything I'm doing wrong until I move on to Native Audio?

Body:
If you want to play audio using an HTML element you should first add it to the body of your html.
If you want a full typescript solution, you can follow the most voted answer on this other stackoverflow question: Play sound in Angular 4

A very easy way to test this. Create an empty index.html file in a folder. Put a WAV file named audio.wav in the same folder. Now open index.html in the browser. Then open DevTools and run this script:

let audio = new Audio();
audio.src = "./audio.wav";
audio.load();
audio.play();

your WAV file should now be correctly reproduced


问:
How can I switch windows in Vim
I am using Vim and I am unable to switch to one of my windows by using the default bind keys <ctrl+w> j. I have three windows open and the bottom right window is inaccessible. Why is this happening?

答:
It appears as if you have taken something similar to the following course of action

```<code>vim <some-file>
:vs <some-other-file>
<C-w> l     // to get to the right window
:term       // to open up a terminal session within right right window
<C-w> j     // to move to the bottom right window (a normal vim window)
:q
vim <file>  // within the terminal inside the right vim window
:sp <file>  // split that window
</code>```

Now it will appear as if you have three vim windows, when in reality, you have four:

Two outer (the left, and the right terminal session)

Two within the right window's terminal session

This is quite a precarious position because whether you are in the outer left or right session, the outer buffer (not sure if this is the correct word so please correct me if I'm wrong) will always captures the <C-w> control character for some reason.

You can see this by looking where the <C-w> shows up on the screen when you press it. If I have replicated your environment correctly, it shows up in the bottom right corner below the outer buffer's right window.

As a workaround to this, instead of using <C-w> to proc window navigation, you need to use:

```<code>:winc j
</code>```

to navigate to the bottom right window.

Title: How can I switch windows in Vim

Body:
It appears as if you have taken something similar to the following course of action

vim <some-file>
:vs <some-other-file>
<C-w> l     // to get to the right window
:term       // to open up a terminal session within right right window
<C-w> j     // to move to the bottom right window (a normal vim window)
:q
vim <file>  // within the terminal inside the right vim window
:sp <file>  // split that window

Now it will appear as if you have three vim windows, when in reality, you have four:

Two outer (the left, and the right terminal session)

Two within the right window's terminal session

This is quite a precarious position because whether you are in the outer left or right session, the outer buffer (not sure if this is the correct word so please correct me if I'm wrong) will always captures the <C-w> control character for some reason.

You can see this by looking where the <C-w> shows up on the screen when you press it. If I have replicated your environment correctly, it shows up in the bottom right corner below the outer buffer's right window.

As a workaround to this, instead of using <C-w> to proc window navigation, you need to use:

:winc j

to navigate to the bottom right window.


问:
How do I stop a function? ( jQuery, .hover() )
When you hover over the squares of the picture change one after another using the interval function. Can't solve 2 problems.
1. The function should be started only at the square on which the point.
2. The function should stop if the cursor has left the square.

Help me think.

$('.block').hover(function(){
    setInterval(myFuncSuper2, 3000);
  });

    // Change pic on hover
    function changePic(i) {
        setTimeout(function () {
            jQuery(".hero-cat_" + i).addClass("active");
            jQuery(".hero-cat_" + i).siblings().removeClass("active")
        }, i * 1000)
    }
    function myFuncSuper2() {
        for (let i = 0; i <= 3; i++) {
            changePic(i);
        }
    }```
<pre class="snippet-code-css lang-css prettyprint-override"><code>.block {
  width: 100px;
  height: 100px;
  border: 1px solid;
  position: relative;
  cursor: pointer;
}

.block img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  position: absolute;
  top: 0;
  display: none;
}

.block img.active {
  display: inline;
}</code>```

```

答:
-- Edit: added clearing the timeouts created in myFuncSuper2 ---

Set the function for hover off, and clear the interval

```<code>var interval = null;
var timeouts = [0,0,0];

$('.hero-category').hover(function () {
  interval = setInterval(myFuncSuper2, 3000)
}, function() {
  if (interval) clearInterval(interval);
  for (var i = 0; i < timeouts.length; i++) {
    if (timeouts[i] !== 0) {
      clearTimeout(timeouts[i]);
    }
  }
});

function myFuncSuper2() {
    for (let i = 0; i <= 3; i++) {
      timeouts[i] = setTimeout(function() {
          jQuery(this).find(".hero-cat_" + i).addClass("active");
          jQuery(this).find(".hero-cat_" + i).siblings().removeClass("active")
      }.bind(this), i * 300)
    }
}
</code>```

Body:
When you hover over the squares of the picture change one after another using the interval function. Can't solve 2 problems.
1. The function should be started only at the square on which the point.
2. The function should stop if the cursor has left the square.

Help me think.

$('.block').hover(function(){
    setInterval(myFuncSuper2, 3000);
  });

    // Change pic on hover
    function changePic(i) {
        setTimeout(function () {
            jQuery(".hero-cat_" + i).addClass("active");
            jQuery(".hero-cat_" + i).siblings().removeClass("active")
        }, i * 1000)
    }
    function myFuncSuper2() {
        for (let i = 0; i <= 3; i++) {
            changePic(i);
        }
    }

.block {
  width: 100px;
  height: 100px;
  border: 1px solid;
  position: relative;
  cursor: pointer;
}

.block img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  position: absolute;
  top: 0;
  display: none;
}

.block img.active {
  display: inline;
}

Body:
-- Edit: added clearing the timeouts created in myFuncSuper2 ---

Set the function for hover off, and clear the interval

var interval = null;
var timeouts = [0,0,0];

$('.hero-category').hover(function () {
  interval = setInterval(myFuncSuper2, 3000)
}, function() {
  if (interval) clearInterval(interval);
  for (var i = 0; i < timeouts.length; i++) {
    if (timeouts[i] !== 0) {
      clearTimeout(timeouts[i]);
    }
  }
});

function myFuncSuper2() {
    for (let i = 0; i <= 3; i++) {
      timeouts[i] = setTimeout(function() {
          jQuery(this).find(".hero-cat_" + i).addClass("active");
          jQuery(this).find(".hero-cat_" + i).siblings().removeClass("active")
      }.bind(this), i * 300)
    }
}


问:
How to Show 2 LatLng as Initial Position in Flutter Google Map
i'm doing (OLA, UBER) like app in flutter.i wanna show route from source and destination and to set initial camera position by covering two lat-long.</p>

```<code>GoogleMap(
                onMapCreated: _onMapCreated,
                mapType: MapType.normal,
                compassEnabled: true,
                myLocationEnabled: true,
                initialCameraPosition: CameraPosition(target:
                LatLng(0.0, 0.0)), // <---- instead of single
                // latlong, i wanna show both source and
                // destination
                markers: _createMarker(),
                polylines: Set<Polyline>.of(polyLines.values),
              ),
</code>```

答:
```<code>await mapController
    .animateCamera(CameraUpdate.newLatLngBounds(
        LatLngBounds(southwest: LatLongONE, northeast: LatLongTWO), 35))
</code>```

those two southwest, northeast will be given by this
enter link description here

google Api

Body:
i'm doing (OLA, UBER) like app in flutter.i wanna show route from source and destination and to set initial camera position by covering two lat-long.

GoogleMap(
                onMapCreated: _onMapCreated,
                mapType: MapType.normal,
                compassEnabled: true,
                myLocationEnabled: true,
                initialCameraPosition: CameraPosition(target:
                LatLng(0.0, 0.0)), // <---- instead of single
                // latlong, i wanna show both source and
                // destination
                markers: _createMarker(),
                polylines: Set<Polyline>.of(polyLines.values),
              ),

Body:
await mapController
    .animateCamera(CameraUpdate.newLatLngBounds(
        LatLngBounds(southwest: LatLongONE, northeast: LatLongTWO), 35))

those two southwest, northeast will be given by this
enter link description here

google Api


问:
How to: Give permissions for text channel when user joins VC and revoke when user leaves VC
I'm attempting to make it so that when someone joins the Voice Channel, so the Bot will add the specific person to the text channel with the permission to read and send messages and remove the individual and their permissions when they leave the Voice Channel. I'm not overly familiar with discord.js so I'm not sure on how to do it.</p>

答:
First and foremost, welcome to Stack Overflow. I hope we can be of help to you.

Let's start by detecting when a member joins a voice channel. To do so, we can listen to your client's voiceStateUpdate event. Next, we can compare the old voice channel with the new one, and see if the member joined or left. Finally, we can change the permissions for the member in the text channel using GuildChannel.overwritePermissions().

Update: Multiple "pairs" of text channels and voice channels with similar behavior.

To do this for many different channels, you could set up a json file to store the voice channels and corresponding text channels, and then iterate over each pair, checking if the situation matches any.

channelPairs.json

```<code>[
  { "voice": "voiceChannelIDHere", "text": "textChannelIDHere" }
]
</code>```

index.js

const pairs = require('./channelPairs.json'); // Keep in mind the path may vary

client.on('voiceStateUpdate', (oldMember, newMember) => {
  let oldID;
  let newID;
  if (oldMember.voiceChannel) oldID = oldMember.voiceChannel.id;
  if (newMember.voiceChannel) newID = newMember.voiceChannel.id;

  for (let i = 0; i < pairs.length; i++) {
    const textChannel = newMember.guild.channels.get(pairs[i].text);
    if (!textChannel) {
      console.log('Invalid text channel ID in json.');
      continue;
    }

    const vcID = pairs[i].voice;

    if (oldID !== vcID && newID === vcID) {          // Joined the voice channel.
      textChannel.overwritePermissions(newMember, {
        VIEW_CHANNEL: true,
        SEND_MESSAGES: true
      }).catch(console.error);
    } else if (oldID === vcID && newID !== vcID) {   // Left the voice channel.
      textChannel.overwritePermissions(newMember, {
        VIEW_CHANNEL: null,
        SEND_MESSAGES: null
      }).catch(console.error);
    }
  }
});
```

Body:
First and foremost, welcome to Stack Overflow. I hope we can be of help to you.

Let's start by detecting when a member joins a voice channel. To do so, we can listen to your client's voiceStateUpdate event. Next, we can compare the old voice channel with the new one, and see if the member joined or left. Finally, we can change the permissions for the member in the text channel using GuildChannel.overwritePermissions().

Update: Multiple "pairs" of text channels and voice channels with similar behavior.

To do this for many different channels, you could set up a json file to store the voice channels and corresponding text channels, and then iterate over each pair, checking if the situation matches any.

channelPairs.json

[
  { "voice": "voiceChannelIDHere", "text": "textChannelIDHere" }
]

index.js

const pairs = require('./channelPairs.json'); // Keep in mind the path may vary

client.on('voiceStateUpdate', (oldMember, newMember) => {
  let oldID;
  let newID;
  if (oldMember.voiceChannel) oldID = oldMember.voiceChannel.id;
  if (newMember.voiceChannel) newID = newMember.voiceChannel.id;

  for (let i = 0; i < pairs.length; i++) {
    const textChannel = newMember.guild.channels.get(pairs[i].text);
    if (!textChannel) {
      console.log('Invalid text channel ID in json.');
      continue;
    }

    const vcID = pairs[i].voice;

    if (oldID !== vcID && newID === vcID) {          // Joined the voice channel.
      textChannel.overwritePermissions(newMember, {
        VIEW_CHANNEL: true,
        SEND_MESSAGES: true
      }).catch(console.error);
    } else if (oldID === vcID && newID !== vcID) {   // Left the voice channel.
      textChannel.overwritePermissions(newMember, {
        VIEW_CHANNEL: null,
        SEND_MESSAGES: null
      }).catch(console.error);
    }
  }
});


问:
Downloading file programmatically with HTTP authentication
I want to download a file (e.g. http://rapidpich.ir/d/555864) programmatically using php. However, when I attempt to follow the link in my web browser, I'm asked for a username and password.

How can I provide these credentials in PHP and retrieve the file?

答:
You can use cURL to submit form data.

Take a look here cURL tutorial and here php cURL


问:
What does a semicolon before an equal sign mean?
My book has the following piece of code. Is it some sort of misprint? I haven't been able to find anything online.</p>

```<code>StackNodePtr tempPtr; = *topPtr;
</code>```

答: It is a misprint. There is absolutely no way that could compile.</p>

Body:
My book has the following piece of code. Is it some sort of misprint? I haven't been able to find anything online.

StackNodePtr tempPtr; = *topPtr;


问:
Typing Immutable.js Map in Typescript
I'm a newbie in Typescript and  i'm trying to strongly type an Immutable Map (immutable.js library).

```<code>type AllowedValue =
    string |
    number |
    boolean |
    AllowedMap |
    AllowedList |
    TypedMap<any> |
    undefined;

interface AllowedList extends List<AllowedValue> {}

interface AllowedMap extends Map<string, AllowedValue> {}

export type MapTypeAllowedData<DataType> = {
    [K in keyof DataType]: AllowedValue;

};

export interface TypedMap<DataType extends MapTypeAllowedData<DataType>> extends Map<string, AllowedValue> {
    toJS(): DataType;
    get<K extends keyof DataType>(key: K, notSetValue?: DataType[K]): DataType[K];
    set<K extends keyof DataType>(key: K, value: DataType[K]): this;

}

const createTypedMap = <DataType extends MapTypeAllowedData<DataType>>(data: DataType): TypedMap<DataType> => Map(data) as any;

</code>```

and I have this error.

```<code>Interface 'TypedMap<DataType>' incorrectly extends interface 'Map<string, AllowedValue>'.
  Types of property 'set' are incompatible.
    Type '<K extends keyof DataType>(key: K, value: DataType[K]) => this' is not assignable to type '(key: string, value: AllowedValue) => this'.
      Types of parameters 'key' and 'key' are incompatible.
        Type 'string' is not assignable to type 'keyof DataType'.
export interface TypedMap<DataType extends MapTypeAllowedData<DataType>>
extends Map<string, AllowedValue> {
                    ~~~~~~~~
</code>```

How can I solve it?

答:
The error is correct... Your TypedMap<DataType> does not act like a Map<string, AllowedValue>.  If I have a Map<string, AllowedValue>, I should be able to call get("randomString") on it.  But TypedMap<DataType> only allows get() to be called with a parameter of type keyof DataType.  So you get an error.

Perhaps you meant that TypedMap<DataType> should act like a Map<keyof DataType, AllowedValue> instead?

```<code>export interface TypedMap<DataType extends MapTypeAllowedData<DataType>>
  extends Map<keyof DataType, AllowedValue> { // changed here

  toJS(): DataType;
  get<K extends keyof DataType>(key: K, notSetValue?: DataType[K]): DataType[K];
  set<K extends keyof DataType>(key: K, value: DataType[K]): this;

}
</code>```

That should hopefully act the way you want.  Good luck!

Title: Typing Immutable.js Map in Typescript

Body:
I'm a newbie in Typescript and  i'm trying to strongly type an Immutable Map (immutable.js library).

type AllowedValue =
    string |
    number |
    boolean |
    AllowedMap |
    AllowedList |
    TypedMap<any> |
    undefined;

interface AllowedList extends List<AllowedValue> {}

interface AllowedMap extends Map<string, AllowedValue> {}

export type MapTypeAllowedData<DataType> = {
    [K in keyof DataType]: AllowedValue;

};

export interface TypedMap<DataType extends MapTypeAllowedData<DataType>> extends Map<string, AllowedValue> {
    toJS(): DataType;
    get<K extends keyof DataType>(key: K, notSetValue?: DataType[K]): DataType[K];
    set<K extends keyof DataType>(key: K, value: DataType[K]): this;

}

const createTypedMap = <DataType extends MapTypeAllowedData<DataType>>(data: DataType): TypedMap<DataType> => Map(data) as any;

and I have this error.

Interface 'TypedMap<DataType>' incorrectly extends interface 'Map<string, AllowedValue>'.
  Types of property 'set' are incompatible.
    Type '<K extends keyof DataType>(key: K, value: DataType[K]) => this' is not assignable to type '(key: string, value: AllowedValue) => this'.
      Types of parameters 'key' and 'key' are incompatible.
        Type 'string' is not assignable to type 'keyof DataType'.
export interface TypedMap<DataType extends MapTypeAllowedData<DataType>>
extends Map<string, AllowedValue> {
                    ~~~~~~~~

How can I solve it?

Body:
The error is correct... Your TypedMap<DataType> does not act like a Map<string, AllowedValue>.  If I have a Map<string, AllowedValue>, I should be able to call get("randomString") on it.  But TypedMap<DataType> only allows get() to be called with a parameter of type keyof DataType.  So you get an error.

Perhaps you meant that TypedMap<DataType> should act like a Map<keyof DataType, AllowedValue> instead?

export interface TypedMap<DataType extends MapTypeAllowedData<DataType>>
  extends Map<keyof DataType, AllowedValue> { // changed here

  toJS(): DataType;
  get<K extends keyof DataType>(key: K, notSetValue?: DataType[K]): DataType[K];
  set<K extends keyof DataType>(key: K, value: DataType[K]): this;

}

That should hopefully act the way you want.  Good luck!


问:
How does adding a record in db using Linq to SQL work?
I am just learning Linq to SQL and from an example I added a record in db by passing a custom type object. For example to add a new user in users table I did:

```<code>db.Users.InsertOnSubmit(newUser);
db.SubmitChanges();
</code>```

I couldn't get how Linq know which property value should be added in which column ?

Is there any better way then this to add a new record in db using Linq ?

Kindly also mention how I can add if I am not using custom types (DTO) ?

so thanks for your precious time and sharing.

答:
Your DBML file spells out how all your objects' properties are mapped to your DBMS.  the database tables/views you add to the DBML causes corresponding classes to be created for you—like your Users class—whose properties are decorated with attributes telling L2S how to handle all the ORM mappings

Under your DBML file should be a [whatever].designer.cs file that shows this.  Here's a sample of what it should look like:

```<code>[global::System.Data.Linq.Mapping.TableAttribute(Name="dbo.Invoices")]
public partial class Invoice : INotifyPropertyChanging, INotifyPropertyChanged
{

    private static PropertyChangingEventArgs emptyChangingEventArgs = new PropertyChangingEventArgs(String.Empty);

    private long _InvoiceId;

    private string _InvoiceNum;

    private decimal _TotalTaxDue;
</code>```

snip

```<code>    [global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_InvoiceId", AutoSync=AutoSync.OnInsert, DbType="BigInt NOT NULL IDENTITY", IsPrimaryKey=true, IsDbGenerated=true)]
    public long InvoiceId
    {
        get
        {
            return this._InvoiceId;
        }
        set
        {
            if ((this._InvoiceId != value))
            {
                this.OnInvoiceIdChanging(value);
                this.SendPropertyChanging();
                this._InvoiceId = value;
                this.SendPropertyChanged("InvoiceId");
                this.OnInvoiceIdChanged();
            }
        }
    }

    [global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_InvoiceNum", DbType="VarChar(15)")]
    public string InvoiceNum
    {
        get
        {
            return this._InvoiceNum;
        }
        set
        {
            if ((this._InvoiceNum != value))
            {
                this.OnInvoiceNumChanging(value);
                this.SendPropertyChanging();
                this._InvoiceNum = value;
                this.SendPropertyChanged("InvoiceNum");
                this.OnInvoiceNumChanged();
            }
        }
    }
</code>```

etc

Body:
I am just learning Linq to SQL and from an example I added a record in db by passing a custom type object. For example to add a new user in users table I did:

db.Users.InsertOnSubmit(newUser);
db.SubmitChanges();

I couldn't get how Linq know which property value should be added in which column ?

Is there any better way then this to add a new record in db using Linq ?

Kindly also mention how I can add if I am not using custom types (DTO) ?

so thanks for your precious time and sharing.

Body:
Your DBML file spells out how all your objects' properties are mapped to your DBMS.  the database tables/views you add to the DBML causes corresponding classes to be created for you—like your Users class—whose properties are decorated with attributes telling L2S how to handle all the ORM mappings

Under your DBML file should be a [whatever].designer.cs file that shows this.  Here's a sample of what it should look like:

[global::System.Data.Linq.Mapping.TableAttribute(Name="dbo.Invoices")]
public partial class Invoice : INotifyPropertyChanging, INotifyPropertyChanged
{

    private static PropertyChangingEventArgs emptyChangingEventArgs = new PropertyChangingEventArgs(String.Empty);

    private long _InvoiceId;

    private string _InvoiceNum;

    private decimal _TotalTaxDue;

snip

    [global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_InvoiceId", AutoSync=AutoSync.OnInsert, DbType="BigInt NOT NULL IDENTITY", IsPrimaryKey=true, IsDbGenerated=true)]
    public long InvoiceId
    {
        get
        {
            return this._InvoiceId;
        }
        set
        {
            if ((this._InvoiceId != value))
            {
                this.OnInvoiceIdChanging(value);
                this.SendPropertyChanging();
                this._InvoiceId = value;
                this.SendPropertyChanged("InvoiceId");
                this.OnInvoiceIdChanged();
            }
        }
    }

    [global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_InvoiceNum", DbType="VarChar(15)")]
    public string InvoiceNum
    {
        get
        {
            return this._InvoiceNum;
        }
        set
        {
            if ((this._InvoiceNum != value))
            {
                this.OnInvoiceNumChanging(value);
                this.SendPropertyChanging();
                this._InvoiceNum = value;
                this.SendPropertyChanged("InvoiceNum");
                this.OnInvoiceNumChanged();
            }
        }
    }

etc