Angular modify and resubmit http.get request using buttons on page - angularjs

I'm pulling data from elastic search using Angular http.get and displaying the output using angular.
The initial concept is working fine, however what I would like to do is add a button to the page to be able to run a frequently required query which will modify the data that is displayed and exclude records containing specific words or phrases.
I think that this can be achieved by having the button set the value of a variable within the scope of the http.get request and then resubmititng the get request.
So far I have:
<body>
<form>
<input type="text" placeholder="RemoveEntires" class="form-control" ng-model="formData.input1">
<input type="button" value="RemoveEntries containing text" ng-click='DocView()'>
</form>
<script>
var app = angular.module('DisplayDoc', []);
var baseUrl = "http://elasticserver:9200/app/_search?q=product:balls";
var queryURL = baseUrl + "+!color:"; + formData.input1;
var completeURL = queryURL + "&sort=DateTime&size=1000&default_operator=AND";
app.controller('DocView', function($scope, $http) {
$http({method: 'GET', url: completeURL})
.success(function(response) {$scope.jsondata = response.hits.hits;});
});
</script>
If I enter "red" in the form, I would like it resubmit the http.get request to elasticsearch which would then exclude the red balls from the balls products that are returned.
This is not currently working for me. Any ideas?

You could do something like this.
Controller:
.controller('MainCtrl', function ($scope, $http) {
$scope.search = '';
var baseUrl = "http://elasticserver:9200/app/_search?q=product:balls+!color:";
$scope.submit = function() {
$http.get(baseUrl + $scope.search + "&sort=DateTime&size=1000&default_operator=AND")
.then(function(response) {
$scope.jsondata = response.hits.hits;
});
}
});
And then build the form like this:
<form novalidate>
<input type="text" ng-model="search">
<button type="submit" ng-click="submit()">Search</button>
</form>

Related

angular ng-repeat to always show even on empty object

Hi I want to post item to server, and with each successful addition, automatically add it to DOM with ng-repeat
<div class="" ng-repeat="book in books" >
<div id="eachBook">{{book.title}}</div>
</div>
to POST the data and also to upload an image file, I use Jquery ajax, and $state.go(".") to reload the current page:
var fd = new FormData();
fd.append("file", bookImage);
$http({
method: 'POST',
url: "/someurl,
data: fd,
headers: {
'Content-Type': undefined
}
}).success(function(Image){
var book_obj = {
bookTitle: bookTitle,
bookImage: Image._id
};
$http.post("url to owner book", book_obj)
.success(function(data){
$scope.bookImage = data.bookImage;
$timeout(function(){
alert("success", "successfully added your book");
$state.transitionTo('book', {}, { reload: true });
},2000);
})
})
The problem is with first addition, the DOM is still empty, and even though I use $state to reload the page, it still not working for the first addition. In the end I need to refresh the page manually by clicking refresh.
after the first addition, it works fine. With each book added, it automatically added to DOM..
Any idea how to automatically start the first one without manually rendering the page? using $timeout to delay the refresh has no effect.
Is it not just a simple post to list on success?
var app = angular.module('myApp', []);
app.controller('bookCtrl', function($scope, $http, $timeout) {
$scope.init = function(){
$scope.title = 'initial book?'
postBook();
};
$scope.books = [];
$scope.post = function() {
postBook();
};
function postBook(){
if (!$scope.title) return;
// timeout to simulate server post
$timeout(function() {
$scope.books.push({title:$scope.title});
$scope.title = null;
}, 1000);
};
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="myApp" ng-controller="bookCtrl" ng-init="init()">
<div class="" ng-repeat="book in books">
<div class="eachBook">{{book.title}}</div>
</div>
<input type="text" ng-model="title" /><button ng-click="post()">save</button>
</div>
EDIT: Not sure why your DOM isn't ready but how about ng-init to accomplish an initial book post?

Passing data from View to Controller in Angularjs

I get data from URL in controller but i need it dynamically
d3.json("http://localhost:2016/get_stats_for?brand_name="+$scope.brand,function(data))
i want to get $scope.brand from textBox in the view
how could i do that ?
EDIT 2
Alternatively, you can use ng-change instead.
app.controller('MyController', function($scope, MyService){
$scope.brand = 'D&G'; //initialize value
$scope.onBrandChange = function(){
MyService.getByBrand($scope.brand).then(function(res){
var result = res.data; //here is your JSON
});
});
});
app.service('MyService', function($http){
this.getByBrand = function(brand){
var URL = "http://localhost:2016/get_stats_forbrand_name="+brand;
return $http.get(URL);
};
});
<div ng-controller='MyController'>
<input type='text' ng-change='onBrandChange()' ng-model-options="{debounce: 100}" ng-model='brand'></input>
</div>
You want to track changes to the variable from the scope?
$scope.$watch('brand', function(newValue, oldValue){
//fetch the json file
});
add the following to the ng-model element on the view
ng-model-options="{debounce: 100}"
The update will occur only if element was unchanged for more than 100ms (so in case of fast typing browser won't be throttled by multiple fetch requests)

Why angularjs controller is not called when i click the button again?

Hi i have a webpage like this,
left side has button,
right side is the area for ng-view (in my case, several checkboxes and submit button)
When i click the button, it'll
1. using the route provider, it'll reach its controller and template URL.
2. The controller will query some info from back end side (node.js)
3. The info above will be used by template URL to display initial checkbox options.
Now this procedure works fine for the 1st time. But when i click the button again, i was hoping it'll call its controller again, but from debugger, seems nothing happened, controller is not called.
So very confused, why is this please ???
in the server side,
app.get('/2getMyDiagValue', function(req, res)
{
console.log("get my diag");
var v1=0, v2=0;
var shellCmd = "... some executable ... ";
exec(shellCmd, function(error, stdout, stderr) {
if(error) {
console.log("Error running getting sid");
} else {
// get v1 and v2 from stdout
}
res.json( {"mystuff1":v1, "mystuff2":v2} );
});
app.post('/2setMyDiagValue', function(req, res)
{
// get the checkbox options from webpage,
// and save them in the backend
}
in the client side,
app.config(['$routeProvider',
function($routeProvider) {
$routeProvider.when('/5MyDiag', {
templateUrl: 'partials/MyDiag.html',
controller: 'MyDiagController'
});
}
]);
app.controller('myDiagController', function($scope, $http, $routeParams, QueryMyService) {
// using http.get() to get existing my setting from server side
QueryMyService.getInfoFromUrl7('/2getMyDiagValue').then(function(result) {
$scope.formData = result.formDataObjects;
}, function(error) {
alert("Error");
} );
$scope.submitForm = function() {
console.log("posting form data ...");
$http.post("/2setMyDiagValue",
JSON.stringify($scope.formData)).success(function(){} );
};
});
app.factory('QueryMyService', function($http, $q, $location) {
var factory = {};
var browserProtocol = 'http';
var address = 'localhost';
var server = browserProtocol + '://' + address;
//////////////////////////////////////////////////////////
factory.getInfoFromUrl7 = function(myUrl) {
var deferred = $q.defer();
$http.get(myUrl).success(function(data) {
deferred.resolve(data);
}).error(function(){
deferred.reject();
});
return deferred.promise;
}
return factory;
}
checkbox webpage itself: MyDiag.html
<form ng-submit="submitForm()" ng-controller="myDiagController">
<div class="control-group" style="color:black">
<label>My Checkbox</label>
<div class="checkbox">
<label class="checbox-inline" >
<input class="big-checkbox" type="checkbox" ng-model="formData.myStuff1"
ng-true-value="1" ng-false-value="0" ng-checked="formData.myStuff1 == 1">
<h4>Message 1</h4>
<input class="big-checkbox" type="checkbox" ng-model="formData.myStuff2"
ng-true-value="1" ng-false-value="0" ng-checked="formData.myStuff2 == 1">
<h4>Message 2</h4>
</label>
</div>
<br>
<input class="btn-primary" type="submit">
</form>
index.html
<div class="container">
<a class="btn btn-md btn-info custom-btn" ng-href="#/5MyDiag">Diagnostics</a>
</div>
Since i need to remove company names in the variable, there might be mismatch, but idea is the same. Thank you for your help.
Talked with guru, it's supposed to be so, if angular feels no change to the web GUI, e.g. in my case, i clicked the same button twice, it won't call the route provider again for the 2nd click.
If you knew this concept, you don't need to read my code to answer this question.
Wish i can get the 4 points back.

AngularJS autocomplete from web service

I'm using REST Countries web service and I want to have an autocomplete feature when user is starting to type in input field, and when some country was selected to display an info about it. Want to do it with factories or maybe a directive, don't know what solution is the best
Here is what I have for now:
REST service link: https://restcountries.eu/
HTML:
<div class="container" ng-controller="CountriesController">
<h3 id="title">Countries Database</h3>
<input type="text" id="countrySearch" ng-model="selected" typeahead="country for country in countries | limitTo:8" />
<ng-view></ng-view>
</div>
Template:
<div ng-controller="CountriesController">
<ul>
<li ng-repeat="country in countries" id="countryInfo">
<p><b>Country:</b> {{country.name}}</p>
<p><b>Native Name:</b> {{country.nativeName}}</p>
<p><b>Capital:</b> {{country.capital}}</p>
<p><b>Region:</b> {{country.region}}</p>
<p><b>Subregion:</b> {{country.subregion}}</p>
<p><b>Borders:</b> {{borders}}</p>
<p><b>Languages:</b> {{languages}}</p>
<p><b>Population:</b> {{country.population}} people</p>
<p><b>Area:</b> {{country.area}} sq.km</p>
<p><b>Currencies:</b> {{currencies}}</p>
<p><b>Timezones:</b> {{timezones}}</p>
<p><b>Calling Code:</b> +{{callingCodes}}</p>
</li>
</ul>
Controller:
app.controller('CountriesController', function ($scope, CountriesFactory) {
CountriesFactory.getCountry().then(function (data) {
$scope.selected = undefined;
$scope.countries = data;
console.log($scope.countries);
$scope.timezones = data[0].timezones.toString();
$scope.languages = data[0].languages.toString();
$scope.currencies = data[0].currencies.toString();
$scope.borders = data[0].borders.toString();
$scope.callingCodes = data[0].callingCodes.toString();
});
});
Factory:
app.factory('CountriesFactory', function ($http, $q) {
return {
getCountry: function () {
var input = $('#countrySearch').val();
var request = 'https://restcountries.eu/rest/v1/name/';
var url = request + input;
return $http.get(url);
}
}
});
Checkout bootstrap UI's autocomplete widget
Look at the source code to see how it is implemented
If you go to rest countries here you can see the example how to get the rest countries like: example
The restcountries.eu/rest/v1/name is not working because they don't expose that page.
Try to make sure you have something into input. Try to check if
$('#countrySearch').val();
is not null or empty first.

Preserve empty field in model with Angular

If I have an angular form like this
<form name="myForm">
<input type="text" required ng-model="field1" />
<input type="text" ng-model="field2" />
</form>
When I access the model it will only hold those fields that have values so if both fields have values json will be {"field1":"value1","field2":"value2"}. If only field1 is has a value json will be {"field1":"value1"}. Can I instruct Angular to keep empty fields in the model with null values?
UPDATE:
My controller looks like below. I'm loading the data as json from the server. When the data comes from the server I get this {"field1":"value1","field2":"value2"} but when saveContent is run and only field1 has a value the server gets this {"field1":"value1"}.
var myApp = angular.module('myApp', []);
myApp.controller('contentEditController', ['$scope', '$http',
function ($scope, $http) {
$scope.saveContent = function () {
$http.post("/api/ContentData", $scope.formdata);
};
$scope.loadContent = function (contentId) {
$http.get("/api/ContentData/" + contentId)
.success(function (response) {
$scope.formdata = response;
});
}
}]);
So fields that had values when they came from the server don't get sent back as empty.
-Mathias
Initialize the values on the scope in the controller,
.controller('formcontroller', [ '$scope', function($scope){
$scope.field1 = "";
$scope.field2 = "";
})];
The proper way to do this is to initialize the variables. You should in your controller have
$scope.field1 = ""
$scope.field2 = ""
or a more crude way to do is in to use ng-init (try not to use ng-init if you can)
<input type="text" required ng-model="field1" ng-init="field1=''"/>
<input type="text" ng-model="field2" ng-init="field2=''"/>

Resources