شركة التطبيقات المتكاملة لتصميم النظم البرمجية الخاصة ش.ش.و.

Integrated Applications Programming Company

Skip Navigation LinksHome » Code Library » Service

Public general use code classes and xml files that we've compiled and used over the years:

Service support class of Next Generation Network'a (NGN's) business model.

   1:  using System.Collections.Generic;
   2:  using System.Data;
   3:  using System.Linq;
   4:  using System.Text.RegularExpressions;
   5:   
   6:  namespace Ia.Ngn.Cl.Model.Business
   7:  {
   8:      ////////////////////////////////////////////////////////////////////////////
   9:   
  10:      /// <summary publish="true">
  11:      /// Service support class of Next Generation Network'a (NGN's) business model.
  12:      /// </summary>
  13:      /// 
  14:      /// <remarks> 
  15:      /// Copyright © 2006-2019 Jasem Y. Al-Shamlan (info@ia.com.kw), Integrated Applications - Kuwait. All Rights Reserved.
  16:      ///
  17:      /// This library is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by
  18:      /// the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
  19:      ///
  20:      /// This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
  21:      /// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
  22:      /// 
  23:      /// You should have received a copy of the GNU General Public License along with this library. If not, see http://www.gnu.org/licenses.
  24:      /// 
  25:      /// Copyright notice: This notice may not be removed or altered from any source distribution.
  26:      /// </remarks> 
  27:      public partial class Service
  28:      {
  29:          private static int sequentialQueueOriginalCount;
  30:          private static Queue<string> sequentialQueue = new Queue<string>();
  31:   
  32:          public static readonly int TemporaryProcedureToIndicateWhereTheLastReadNumberFromOracleDatabaseBecauseListIsTooLongToRepeatHahaha = 24667538;
  33:   
  34:          /// <summary/>
  35:          public static readonly List<string> AllowedToBeMigratedOltSymbolList = new List<string>() { "EGL", "SAB", "COB", "FNT", "BYN", "MSF", "MBA" };
  36:   
  37:          /// <summary/>
  38:          public enum SupplementaryService
  39:          {
  40:              CallerId = 1, InternationalCalling, InternationalCallingUserControlled, CallForwarding, CallWaiting, ConferenceCall, WakeupCall, AbbriviatedCalling, ServiceSuspension
  41:          };
  42:   
  43:          ////////////////////////////////////////////////////////////////////////////
  44:   
  45:          /// <summary>
  46:          ///
  47:          /// </summary>
  48:          public static int CountryCode { get { return 965; } }
  49:   
  50:          ////////////////////////////////////////////////////////////////////////////
  51:   
  52:          /// <summary>
  53:          ///
  54:          /// </summary>
  55:          public class ServiceSupplementaryService
  56:          {
  57:              public int Service { get; set; }
  58:              public string Pin { get; set; }
  59:              public bool SubscriberHasPin { get; set; }
  60:              public bool InternationalCallingUserControlledActivated { get; set; }
  61:              public bool ServiceAdministrativelySuspendedByBillingDepartment { get; set; }
  62:              public bool ServiceAdministrativelySuspendedForOtherReasons { get; set; }
  63:              public bool IsPbx { get; set; }
  64:   
  65:              public List<Ia.Ngn.Cl.Model.Business.Service.SupplementaryService> SupplementaryServiceList { get; set; }
  66:   
  67:              public ServiceSupplementaryService()
  68:              {
  69:                  this.Service = 0;
  70:                  this.Pin = string.Empty;
  71:                  this.SubscriberHasPin = false;
  72:                  this.InternationalCallingUserControlledActivated = false;
  73:                  this.ServiceAdministrativelySuspendedByBillingDepartment = false;
  74:                  this.ServiceAdministrativelySuspendedForOtherReasons = false;
  75:                  this.IsPbx = false;
  76:   
  77:                  this.SupplementaryServiceList = new List<Ia.Ngn.Cl.Model.Business.Service.SupplementaryService>();
  78:              }
  79:          }
  80:   
  81:          ////////////////////////////////////////////////////////////////////////////
  82:   
  83:          /// <summary>
  84:          ///
  85:          /// </summary>
  86:          public class ServiceType
  87:          {
  88:              /// <summary/>
  89:              public int Id { get; set; }
  90:              /// <summary/>
  91:              public string Name { get; set; }
  92:              /// <summary/>
  93:              public string NameArabicName { get; set; }
  94:              /// <summary/>
  95:              public string Color { get; set; }
  96:   
  97:              /// <summary/>
  98:              public ServiceType(int id, string name, string nameArabicName, string color)
  99:              {
 100:                  this.Id = id;
 101:                  this.Name = name;
 102:                  this.NameArabicName = nameArabicName;
 103:                  this.Color = color;
 104:              }
 105:   
 106:              /// <summary/>
 107:              public string ColoredNameArabicName
 108:              {
 109:                  get
 110:                  {
 111:                      return @"<span class=""" + this.Color + @""">" + this.NameArabicName + @"</span>";
 112:                  }
 113:              }
 114:   
 115:              /// <summary/>
 116:              public static int GponService
 117:              {
 118:                  get
 119:                  {
 120:                      return (from s in Ia.Ngn.Cl.Model.Data.Service.ServiceTypeList where s.Name == "Ngn" select s.Id).Single();
 121:                  }
 122:              }
 123:   
 124:              /// <summary/>
 125:              public static int PstnService
 126:              {
 127:                  get
 128:                  {
 129:                      return (from s in Ia.Ngn.Cl.Model.Data.Service.ServiceTypeList where s.Name == "Pstn" select s.Id).Single();
 130:                  }
 131:              }
 132:   
 133:              ////////////////////////////////////////////////////////////////////////////
 134:              ////////////////////////////////////////////////////////////////////////////
 135:          }
 136:   
 137:          ////////////////////////////////////////////////////////////////////////////
 138:   
 139:          /// <summary>
 140:          ///
 141:          /// </summary>
 142:          public Service() { }
 143:   
 144:          ////////////////////////////////////////////////////////////////////////////
 145:   
 146:          /// <summary>
 147:          ///
 148:          /// </summary>
 149:          public static string ServiceName(string service, int serviceType)
 150:          {
 151:              string name;
 152:   
 153:              name = service;
 154:   
 155:              if (name == "0") name = string.Empty;
 156:   
 157:              return name;
 158:          }
 159:   
 160:          ////////////////////////////////////////////////////////////////////////////
 161:   
 162:          /// <summary>
 163:          ///
 164:          /// </summary>
 165:          public static string ServiceIdToService(string serviceId)
 166:          {
 167:              string service;
 168:   
 169:              service = serviceId.Substring(0, serviceId.IndexOf(":"));
 170:   
 171:              return service;
 172:          }
 173:   
 174:          ////////////////////////////////////////////////////////////////////////////
 175:   
 176:          /// <summary>
 177:          ///
 178:          /// </summary>
 179:          public static string ServiceToServiceId(string service, int serviceType)
 180:          {
 181:              string serviceId;
 182:   
 183:              serviceId = service + ":" + serviceType + ":" + Ia.Ngn.Cl.Model.Business.Service.CountryCode;
 184:   
 185:              return serviceId;
 186:          }
 187:   
 188:          ////////////////////////////////////////////////////////////////////////////
 189:   
 190:          /// <summary>
 191:          ///
 192:          /// </summary>
 193:          public static int ServiceIdToServiceType(string serviceId)
 194:          {
 195:              int serviceType;
 196:   
 197:              serviceType = int.Parse(serviceId.Substring(serviceId.IndexOf(":") + 1, 1));
 198:   
 199:              return serviceType;
 200:          }
 201:   
 202:          ////////////////////////////////////////////////////////////////////////////
 203:   
 204:          /// <summary>
 205:          ///
 206:          /// </summary>
 207:          public static bool ServiceStringFormatIsLegal(string service)
 208:          {
 209:              bool b;
 210:   
 211:              if (!string.IsNullOrEmpty(service))
 212:              {
 213:                  b = Regex.IsMatch(service, @"^\d{8}$");
 214:              }
 215:              else b = false;
 216:   
 217:              return b;
 218:          }
 219:   
 220:          ////////////////////////////////////////////////////////////////////////////
 221:   
 222:          /// <summary>
 223:          ///
 224:          /// </summary>
 225:          public class KuwaitNgnArea
 226:          {
 227:              /// <summary/>
 228:              public KuwaitNgnArea() { }
 229:   
 230:              /// <summary/>
 231:              public KuwaitNgnArea(string name, string arabicName)
 232:              {
 233:                  this.Name = name;
 234:                  this.ArabicName = arabicName;
 235:              }
 236:   
 237:              /// <summary/>
 238:              public int Id { get; set; }
 239:   
 240:              /// <summary/>
 241:              public string Name { get; set; }
 242:   
 243:              /// <summary/>
 244:              public string ArabicName { get; set; }
 245:   
 246:              /// <summary/>
 247:              public string NameArabicName
 248:              {
 249:                  get
 250:                  {
 251:                      return Name + " (" + ArabicName + ")";
 252:                  }
 253:              }
 254:   
 255:              /// <summary/>
 256:              public string Symbol { get; set; }
 257:   
 258:              /// <summary/>
 259:              public string ServiceRequestAddressProvinceAreaName { get; set; }
 260:   
 261:              /// <summary/>
 262:              public virtual List<Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Site> SiteList { get; set; }
 263:          }
 264:   
 265:          ////////////////////////////////////////////////////////////////////////////
 266:   
 267:          /// <summary>
 268:          ///
 269:          /// </summary>
 270:          public static List<int> SelectListOfNumbersWithinAllowedDomainList(List<int> inNumberList)
 271:          {
 272:              string numberString;
 273:              List<int> numberList;
 274:   
 275:              numberList = new List<int>();
 276:   
 277:              if (inNumberList.Count > 0)
 278:              {
 279:                  numberList = new List<int>(inNumberList.Count);
 280:   
 281:                  foreach (int i in inNumberList)
 282:                  {
 283:                      numberString = i.ToString();
 284:   
 285:                      if (NumberIsWithinAllowedDomainList(numberString)) numberList.Add(i);
 286:                  }
 287:              }
 288:   
 289:              return numberList;
 290:          }
 291:   
 292:          ////////////////////////////////////////////////////////////////////////////
 293:   
 294:          /// <summary>
 295:          ///
 296:          /// </summary>
 297:          public static bool OltIsWithinAllowedToBeProvisionedOltList(Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Olt olt)
 298:          {
 299:              return Ia.Ngn.Cl.Model.Data.Service.AllowedToBeProvisionedOltList.Any(u => u == olt);
 300:          }
 301:   
 302:          ////////////////////////////////////////////////////////////////////////////
 303:   
 304:          /// <summary>
 305:          ///
 306:          /// </summary>
 307:          public static bool OltIsWithinAllowedToBeMigratedOltList(Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Olt olt)
 308:          {
 309:              return Ia.Ngn.Cl.Model.Data.Service.AllowedToBeMigratedOltList.Any(u => u == olt);
 310:          }
 311:   
 312:          ////////////////////////////////////////////////////////////////////////////
 313:   
 314:          /// <summary>
 315:          ///
 316:          /// </summary>
 317:          public static bool OltIdIsWithinAllowedToBeMigratedOltList(int oltId)
 318:          {
 319:              return Ia.Ngn.Cl.Model.Data.Service.AllowedToBeMigratedOltIdList.Contains(oltId);
 320:          }
 321:   
 322:          ////////////////////////////////////////////////////////////////////////////
 323:   
 324:          /// <summary>
 325:          ///
 326:          /// </summary>
 327:          public static bool OltIsWithinAllowedToBeProvisionedOrMigratedOltList(Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Olt olt)
 328:          {
 329:              return Ia.Ngn.Cl.Model.Data.Service.AllowedToBeProvisionedOltList.Any(u => u == olt) || Ia.Ngn.Cl.Model.Data.Service.AllowedToBeMigratedOltList.Any(u => u == olt);
 330:          }
 331:   
 332:          ////////////////////////////////////////////////////////////////////////////
 333:   
 334:          /// <summary>
 335:          ///
 336:          /// </summary>
 337:          public static bool AreaSymbolIsWithinAnAllowedOltToBeProvisionedDomainList(string areaSymbol)
 338:          {
 339:              bool b;
 340:   
 341:              if (!string.IsNullOrEmpty(areaSymbol))
 342:              {
 343:                  b = Ia.Ngn.Cl.Model.Data.Service.AllowedToBeProvisionedOltList.Any(v => v.Odf.Router.Site.AreaSymbolList.Any(u => areaSymbol == u));
 344:              }
 345:              else
 346:              {
 347:                  b = false;
 348:              }
 349:   
 350:              return b;
 351:          }
 352:   
 353:          ////////////////////////////////////////////////////////////////////////////
 354:   
 355:          /// <summary>
 356:          ///
 357:          /// </summary>
 358:          public static bool NumberIsWithinAnAllowedOltToBeProvisionedDomainList(string service)
 359:          {
 360:              bool b;
 361:   
 362:              if (!string.IsNullOrEmpty(service))
 363:              {
 364:                  b = Ia.Ngn.Cl.Model.Data.Service.AllowedToBeProvisionedOltList.Any(v => v.Odf.Router.DomainList.Any(u => service.StartsWith(u.ToString())));
 365:              }
 366:              else
 367:              {
 368:                  b = false;
 369:              }
 370:   
 371:              return b;
 372:          }
 373:   
 374:          ////////////////////////////////////////////////////////////////////////////
 375:   
 376:          /// <summary>
 377:          ///
 378:          /// </summary>
 379:          public static bool NumberIsWithinAllowedDomainList(long number)
 380:          {
 381:              string numberString;
 382:   
 383:              numberString = number.ToString();
 384:   
 385:              return NumberIsWithinAllowedDomainList(numberString);
 386:          }
 387:   
 388:          ////////////////////////////////////////////////////////////////////////////
 389:   
 390:          /// <summary>
 391:          ///
 392:          /// </summary>
 393:          public static bool NumberIsWithinAllowedRouterDomainList(Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Ont ont, string service)
 394:          {
 395:              bool b;
 396:   
 397:              if (ont != null)
 398:              {
 399:                  b = ont.Pon.PonGroup.Olt.Odf.Router.DomainList.Any(u => service.StartsWith(u.ToString()));
 400:              }
 401:              else b = false;
 402:   
 403:              return b;
 404:          }
 405:   
 406:          ////////////////////////////////////////////////////////////////////////////
 407:   
 408:          /// <summary>
 409:          ///
 410:          /// </summary>
 411:          public static bool NumberIsWithinAllowedDomainList(string number)
 412:          {
 413:              bool isWithinAllowed;
 414:   
 415:              if (!string.IsNullOrEmpty(number))
 416:              {
 417:                  if (Ia.Ngn.Cl.Model.Data.Service.DomainList.Any(u => number.StartsWith(u.ToString()))) isWithinAllowed = true;
 418:                  else isWithinAllowed = false;
 419:              }
 420:              else isWithinAllowed = false;
 421:   
 422:              return isWithinAllowed;
 423:          }
 424:   
 425:          ////////////////////////////////////////////////////////////////////////////
 426:   
 427:          /// <summary>
 428:          ///
 429:          /// </summary>
 430:          public static bool NumberIsWithinAllowedNokiaSwitchDomainList(long number)
 431:          {
 432:              string numberString;
 433:   
 434:              numberString = number.ToString();
 435:   
 436:              return NumberIsWithinAllowedNokiaSwitchDomainList(numberString);
 437:          }
 438:   
 439:          ////////////////////////////////////////////////////////////////////////////
 440:   
 441:          /// <summary>
 442:          ///
 443:          /// </summary>
 444:          public static bool NumberIsWithinAllowedNokiaSwitchDomainList(string number)
 445:          {
 446:              bool isWithinAllowedDomains;
 447:   
 448:              if (NumberIsWithinAllowedDomainList(number))
 449:              {
 450:                  if (Ia.Ngn.Cl.Model.Data.Service.NokiaSwitchDomainList.Any(u => number.StartsWith(u.ToString()))) isWithinAllowedDomains = true;
 451:                  else isWithinAllowedDomains = false;
 452:              }
 453:              else isWithinAllowedDomains = false;
 454:   
 455:              return isWithinAllowedDomains;
 456:          }
 457:   
 458:          ////////////////////////////////////////////////////////////////////////////
 459:   
 460:          /// <summary>
 461:          ///
 462:          /// </summary>
 463:          public static bool NumberIsWithinAllowedHuaweiSwitchDomainList(long number)
 464:          {
 465:              string numberString;
 466:   
 467:              numberString = number.ToString();
 468:   
 469:              return NumberIsWithinAllowedHuaweiSwitchDomainList(numberString);
 470:          }
 471:   
 472:          ////////////////////////////////////////////////////////////////////////////
 473:   
 474:          /// <summary>
 475:          ///
 476:          /// </summary>
 477:          public static bool NumberIsWithinAllowedHuaweiSwitchDomainList(string number)
 478:          {
 479:              bool isWithinAllowedDomains;
 480:   
 481:              if (NumberIsWithinAllowedDomainList(number))
 482:              {
 483:                  if (Ia.Ngn.Cl.Model.Data.Service.HuaweiSwitchDomainList.Any(u => number.StartsWith(u.ToString()))) isWithinAllowedDomains = true;
 484:                  else isWithinAllowedDomains = false;
 485:              }
 486:              else isWithinAllowedDomains = false;
 487:   
 488:              return isWithinAllowedDomains;
 489:          }
 490:   
 491:          ////////////////////////////////////////////////////////////////////////////
 492:   
 493:          /// <summary>
 494:          ///
 495:          /// </summary>
 496:          public static Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor SwitchVendor(string service)
 497:          {
 498:              Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor vendor;
 499:   
 500:              if (NumberIsWithinAllowedNokiaSwitchDomainList(service))
 501:              {
 502:                  vendor = Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor.Nokia;
 503:              }
 504:              else if (NumberIsWithinAllowedHuaweiSwitchDomainList(service))
 505:              {
 506:                  vendor = Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor.Huawei;
 507:              }
 508:              else vendor = Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor.Undefined;
 509:   
 510:              return vendor;
 511:          }
 512:   
 513:          ////////////////////////////////////////////////////////////////////////////
 514:   
 515:          /// <summary>
 516:          ///
 517:          /// </summary>
 518:          public static Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor AccessVendor(string accessName)
 519:          {
 520:              Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor vendor;
 521:   
 522:              vendor = (from v in Ia.Ngn.Cl.Model.Data.NetworkDesignDocument.OntList where v.Access.Name == accessName select v.Pon.PonGroup.Olt.Odf.Vendor).SingleOrDefault();
 523:   
 524:              if (vendor == null) vendor = Ia.Ngn.Cl.Model.Business.NetworkDesignDocument.Vendor.Undefined;
 525:   
 526:              return vendor;
 527:          }
 528:   
 529:          ////////////////////////////////////////////////////////////////////////////
 530:   
 531:          /// <summary>
 532:          ///
 533:          /// </summary>
 534:          public static int ConvertEmsVoipPstnUsersPnToServiceRequestServicePosition(int pn)
 535:          {
 536:              /*
 537:               * - All Nokia ONTs (SFUs and MDUs) start at port position 1
 538:               * - Huawei ONTs (SFUs) start at port position 1, while Huawei MDUs start at port position 0
 539:               * - All positions in the Customer Department database will start at position 1 (e.g. port 3 in a Huawei MDU is 4 in the Customer Department database)
 540:               */
 541:   
 542:              // +1 because it has a Huawei MDU. See above.
 543:   
 544:              return pn + 1;
 545:          }
 546:   
 547:          ////////////////////////////////////////////////////////////////////////////
 548:   
 549:          /// <summary>
 550:          ///
 551:          /// </summary>
 552:          public static int ConvertServiceRequestServicePositionToEmsVoipPstnUsersPn(int servicePosition)
 553:          {
 554:              /*
 555:               * - All Nokia ONTs (SFUs and MDUs) start at port position 1
 556:               * - Huawei ONTs (SFUs) start at port position 1, while Huawei MDUs start at port position 0
 557:               * - All positions in the Customer Department database will start at position 1 (e.g. port 3 in a Huawei MDU is 4 in the Customer Department database)
 558:               */
 559:   
 560:              // -1 because it has a Huawei MDU. See above.
 561:   
 562:              return servicePosition - 1;
 563:          }
 564:   
 565:          ////////////////////////////////////////////////////////////////////////////
 566:   
 567:          /// <summary>
 568:          ///
 569:          /// </summary>
 570:          public static int ConvertFlatTermIdPositionToEmsVoipPstnUsersPn(int flatTermId)
 571:          {
 572:              /*
 573:               * - All Nokia ONTs (SFUs and MDUs) start at port position 1
 574:               * - Huawei ONTs (SFUs) start at port position 1, while Huawei MDUs start at port position 0
 575:               * - All positions in the Customer Department database will start at position 1 (e.g. port 3 in a Huawei MDU is 4 in the Customer Department database)
 576:               */
 577:   
 578:              // -1 because it has a Huawei MDU. See above.
 579:   
 580:              return flatTermId - 1;
 581:          }
 582:   
 583:          ////////////////////////////////////////////////////////////////////////////    
 584:   
 585:          /// <summary>
 586:          ///
 587:          /// </summary>
 588:          public static string SequentialServiceNotInServiceRequestServiceManager(out int sequentialQueueCount, out string progressCounterString)
 589:          {
 590:              string service;
 591:   
 592:              if (sequentialQueue.Count == 0)
 593:              {
 594:                  var list = Ia.Ngn.Cl.Model.Data.Service.ServiceNotInServiceRequestServiceList();
 595:                  sequentialQueue = new Queue<string>(list);
 596:   
 597:                  sequentialQueueOriginalCount = sequentialQueue.Count;
 598:              }
 599:   
 600:              if (sequentialQueue.Count > 0) service = sequentialQueue.Dequeue();
 601:              else service = string.Empty;
 602:   
 603:              progressCounterString = "(" + sequentialQueue.Count + "/" + sequentialQueueOriginalCount + ")";
 604:   
 605:              sequentialQueueCount = sequentialQueue.Count;
 606:   
 607:              return service;
 608:          }
 609:   
 610:          ////////////////////////////////////////////////////////////////////////////    
 611:          ////////////////////////////////////////////////////////////////////////////
 612:      }
 613:   
 614:      ////////////////////////////////////////////////////////////////////////////
 615:   
 616:      /// <summary>
 617:      ///
 618:      /// </summary>
 619:      public static class ServiceExtension
 620:      {
 621:          ////////////////////////////////////////////////////////////////////////////
 622:   
 623:          /// <summary>
 624:          /// 
 625:          /// <see cref="http://stackoverflow.com/questions/8910588/how-to-override-contains"/>
 626:          /// </summary>
 627:          public static bool Contains(this List<Ia.Ngn.Cl.Model.Business.ServiceRequest.NumberSerial> sourceList, int number, int serial)
 628:          {
 629:              return ((from n in sourceList where n.Number == number && n.Serial == serial select n) != null);
 630:          }
 631:   
 632:          ////////////////////////////////////////////////////////////////////////////    
 633:   
 634:          /// <summary>
 635:          ///
 636:          /// </summary>
 637:          public static List<long> IdList(this List<Ia.Ngn.Cl.Model.Business.ServiceRequest.NumberSerial> sourceList)
 638:          {
 639:              return ((from n in sourceList select (long)((long)n.Number * 100 + n.Serial)).ToList());
 640:          }
 641:   
 642:          ////////////////////////////////////////////////////////////////////////////
 643:          ////////////////////////////////////////////////////////////////////////////
 644:      }
 645:   
 646:      ////////////////////////////////////////////////////////////////////////////
 647:      ////////////////////////////////////////////////////////////////////////////   
 648:  }