Filter data from Stream in Flutter/Dart - flutter

I have a Stream which contains List of objects. i.e. List<ProductSubCategoryListModel> and
ProductSubCategoryListModel contains isSelected boolean and CategoryId int.
I want to filter Stream which only has isSelected == true and get list type of List<ProductSubCategoryListModel> in return. After this need to get all the CategoryId from `List.
Here's my code.
Future<void> fetchProducts(
TrendingCategoriesModel categoryModel, int pageIndex) async {
_localCategoryModel = categoryModel;
//Stream I want to manipulate to get List<ProductSubCategoryListModel>
var stream = _categoryListController.stream;
var request = ProductListRequestModel();
var searchParameterModel = SearchParams();
searchParameterModel.SearchText = '';
searchParameterModel.CategoryIDs = //List<int> of CategoryIds filtered from List<ProductSubCategoryListModel>;
searchParameterModel.SubCategoryIDs = null;
searchParameterModel.AttributeIDs = null;
searchParameterModel.SubAttributeIDs = null;
searchParameterModel.StartPrice = 0;
searchParameterModel.EndPrice = null;
searchParameterModel.EndPrice = null;
request.PageIndex = pageIndex;
request.PageSize = 10;
request.SortExpression = '';
request.SortType = '';
request.IsGetFilterData = true;
request.searchParams = searchParameterModel;
if (!_productListController.isClosed) _productListController.sink.add(null);
var response =
await _networkHandler.callAPI(NetworkUrl.PRODUCT_LIST, request);
if (response != null) {
}
}

You can use map method https://api.flutter.dev/flutter/dart-async/Stream/map.html. it returns new stream with mapped data. Map will be applied to each event in a stream.
Additionally you can apply distinct method https://api.flutter.dev/flutter/dart-async/Stream/distinct.html just after map, if you need to ensure that only unique values will be emitted to the subscriber

Related

How to join two firebase queries in the same Stream?

I am using Streambuilder to display a list of tasks. For this I want to join two queries in Firebase: The tasks that have been completed in the last 7 days (alList1) and all the pending tasks (alList2)
The way I do the query is as follows:
Stream<List<AlarmaModel>> cargarAlarmasStream(int fechaMinima) {
final List<AlarmaModel> alarmaListVacia = [];
Query resp = db.child('alarmas').orderByChild('fechaCompleta').startAt(fechaMinima);
final streamPublish1 = resp.onValue.map((event) {
if(event.snapshot.value != null) {
final alList1 = Map<String,dynamic>.from(event.snapshot.value).entries.map((e) {
AlarmaModel alTemp = new AlarmaModel();
alTemp = AlarmaModel.fromJson(Map<String,dynamic>.from(e.value));
alTemp.idAlarma = e.key;
return alTemp;
}).toList();
return alList1;
} else return alarmaListVacia;
});
Query resp2 = db.child('alarmas').orderByChild('completa').equalTo(false);
final streamPublish2 = resp2.onValue.map((event) {
if(event.snapshot.value != null) {
final alList2 = Map<String,dynamic>.from(event.snapshot.value).entries.map((e) {
AlarmaModel alTemp2 = new AlarmaModel();
alTemp2 = AlarmaModel.fromJson(Map<String,dynamic>.from(e.value));
alTemp2.idAlarma = e.key;
return alTemp2;
}).toList();
return alList2;
} else return alarmaListVacia;
});
return streamPublish1;
}
However, at the time of displaying it on the screen with the StreamBuilder, it is only showing me alList1, which is the one contained in streamPublish1. How can I do in the return to output the result of StreamPublish1 added to StreamPublish2?
UPDATE
I was testing the solution in Stackoverflow 36571924 as follows:
Stream<List<AlarmaModel>> pubStream = StreamGroup.merge([streamPublish1, streamPublish2]);
return pubStream
It was close, but it didn't work. It only retrieves the last list (alList2) and not the combination of both.

Flutter - Function - Return Array

I've build an List with 44 places:
List<String> departmentdes = new List(44);
after that I've called a function:
postDepartment();
The function is an api call:
postDepartment() async {
final response = await http.get('url');
final jsonresponse = json.decode(response.body);
List<Department> departments = [];
for(var d in jsonresponse) {
Department department = Department(
fid: d["fid"].toString(),
);
departments.add(department);
}
int index = departments.length -1;
for(int i = 0; i<=index; i++) {
departmentdes[i] = departments[i].fid;
}
return departmentdes;
}
After the postDepartment(); I want to print the departmentdes but it always returns null. Why?
i < index
You're already defining index to be length -1
Just a little logic error.
Change your postDepartment to this and see if it helps:
Future<void> postDepartment() async {
final response = await http.get('url');
final jsonresponse = json.decode(response.body);
List<Department> departments = [];
for(var d in jsonresponse) {
Department department = Department(
fid: d["fid"].toString(),
);
departments.add(department);
}
int index = departments.length -1;
for(int i = 0; i<=index; i++) {
departmentdes[i] = departments[i].fid;
}
return departmentdes;
}
Also check if your departments is not null.

Trying to Move Cards

I am trying to move a card I have found using the search function from one list to another on the same board.
I have tried to set up a new list using the a new factory.list and searching for the list using FirstorDefault LINQ Query but keep getting an Error.
Below is some code I have tried to move my cards.
string query = jnum;
var search = factory.Search(query, 1, SearchModelType.Cards, new IQueryable[] { board });
await search.Refresh();
var CardList = search.Cards.ToList();
foreach (var card in CardList)
{
string tName = card.Name.Substring(0, 6);
if (tName == jnum.Trim())
{
cardid = card.Id;
}
}
var FoundCard = factory.Card(cardid);
string FoundListid = FoundCard.List.Id;
var fromlist = factory.List(FoundListid);
if (Item != null)
{
if (mail.Body.ToUpper().Contains("Approved for Print".ToUpper()))
{
//var ToList = factory.List("5db19603e4428377d77963b4");
var ToList = board.Lists.FirstOrDefault(l => l.Name == "Signed Off");
FoundCard.List = ToList;
// from on proof
//MessageBox.Show("Approved for Print");
}
else if (mail.Body.ToUpper().Contains("Awaiting Review".ToUpper()))
{
//var ToList = factory.List("5db19603e4428377d77963b3");
var ToList = board.Lists.FirstOrDefault(l => l.Name == "On Proof");
FoundCard.List = ToList;
// from in progress or to start
// MessageBox.Show("Awaiting Review");
}
else if (mail.Body.ToUpper().Contains("Amends".ToUpper()))
{
var ToList = factory.List("5dc9442eb245e60a39b3d4a7");
FoundCard.List = ToList;
// from on proof
//MessageBox.Show("Amends");
}
else
{
// non job mail
}
}
I keep getting a is not a valid value Error.
Thanks for help

When using NumericField, get absolutely nothing back every time

Been playing with Lucene.NET the last two days.
After reading up on Dates, I was led to believe that Dates are best converted to Milliseconds, and stored in NumericField, with Indexing=true, and Store=No.
But now nothing ever returns - it must be something basic, but I'm just not seeing it.
The saving code is as follows:
...
else if (type == typeof (DateTime?))
{
var typedValue = (DateTime?) value;
field = numericField = new NumericField(documentFieldName, 4, Field.Store.YES, true);
long milliseconds = typedValue.HasValue?(typedValue.Value.Date.Ticks/TimeSpan.TicksPerMillisecond):0;
numericField.SetLongValue(milliseconds);
doc.Add(numericField);
}
...
else
{
field = stringField = new Field(
documentFieldName,
(value != null)?value.ToString():string.Empty,
Store.YES,
Field.Index.ANALYZED) ;
doc.Add(stringField);
}
// Write the Document to the catalog
indexWriter.AddDocument(doc);
When I query for docs against the values saved in Field ... no problem.
When I query for documents by matching against the values in NumericFields, nothing returns.
Where did I go wrong?
Thanks for your help.
Lucene.Net.Analysis.Analyzer analyzer = new Lucene.Net.Analysis.Standard.StandardAnalyzer(Lucene.Net.Util.Version.LUCENE_30);
var q2 = NumericRangeQuery.NewLongRange("Val", 3, 3, true, true);
var uxy2 = documentSearchManagementService.Search("Students", termQuery, "Id");
Using:
public ScoredDocumentResult[] Search(string indexName, Query query, params string[] hitFieldNamesToReturn)
{
if (_configuration.IndexRootDirectory.IsNullOrEmpty())
{
throw new Exception("Configuration.IndexRootDirectory has not been configued yet.");
}
indexName.ValidateIsNotNullOrEmpty("indexName");
hitFieldNamesToReturn.ValidateIsNotDefault("hitFieldNamesToReturn");
//Specify the index file location where the indexes are to be stored
string indexFileLocation = Path.Combine(_configuration.IndexRootDirectory, indexName);
Lucene.Net.Store.Directory luceneDirectory = Lucene.Net.Store.FSDirectory.Open(indexFileLocation);
IndexSearcher indexSearcher = new IndexSearcher(luceneDirectory);
TopScoreDocCollector topScoreDocCollector = TopScoreDocCollector.Create(10, true);
indexSearcher.Search(query, topScoreDocCollector);
List<ScoredDocumentResult> results = new List<ScoredDocumentResult>();
foreach (var scoreDoc in topScoreDocCollector.TopDocs(0, 10).ScoreDocs)
{
ScoredDocumentResult resultItem = new ScoredDocumentResult();
Lucene.Net.Documents.Document doc = indexSearcher.Doc(scoreDoc.Doc);
resultItem.Score = scoreDoc.Score;
List<ScoredDocumentFieldResult> fields = new List<ScoredDocumentFieldResult>();
foreach (string fieldName in hitFieldNamesToReturn)
{
string fieldValue = doc.Get(fieldName);
fields.Add(new ScoredDocumentFieldResult{Key= fieldName,Value=fieldValue});
}
resultItem.FieldValues = fields.ToArray();
results.Add(resultItem);
}
indexSearcher.Close();
return results.ToArray();
}

MongoDB/Mongoose .find() equal to true/false where null==true

Trying to simplify this snippet into a one liner.
var conditions = [{key: isTrueOrFalse}];
if (isTrueOrFalse)
conditions.push({key: null});
query.find({$or: conditions});
The key, by default, isn't set in the model.
I wrote this util function to make it a one liner, but I'd prefer to use something built into mongoose if possible.
var findWithDefaultIfNull = function(query, key, value, defaultValue) {
var conditions = [];
var condition = {};
condition[key] = value;
conditions.push(condition);
if (value == defaultValue) {
condition = {};
condition[key] = null;
conditions.push(condition);
}
console.log(conditions);
query.find({$or: conditions});
};
exports.findWithDefaultIfNull = findWithDefaultIfNull;