Instalar o Angular
Este comando instala a versão mais recente
npm install -g @angular/cli
Este comando é para escolher a versão que queremos instalar, colocamos o “@” e o numero da versão desejada.
npm install -g @angular/cli@10
As versões que estamos usando no curso:
Verficar a versão do Angular.
ng v
Criar um projeto.
ng new nome_do_projeto
Para criar o diretório:
Clicar com o botão direito em “app” -> new folder -> digitar o nome do diretorio
Para criar a classe:
Clicar com o botão direito em app -> new file…
Node.js é uma plataforma construída sobre o motor JavaScript do Google Chrome para facilmente construir aplicações de rede rápidas e escaláveis. Node.js usa um modelo de I/O direcionada a evento não bloqueante que o torna leve e eficiente, ideal para aplicações em tempo real com troca intensa de dados através de dispositivos distribuídos.
Node.js é um interpretador, com código aberto, de código JavaScript de modo assíncrono e orientado a eventos, focado em migrar a programação do Javascript do lado do cliente para os servidores, criando assim aplicações de alta escalabilidade (como um servidor web), capazes de manipular milhares de conexões/requisições simultâneas em tempo real, numa única máquina física. O Node.js é baseado no interpretador V8 JavaScript Engine (interpretador de JavaScript open source implementado pelo Google em C++ e utilizado pelo Chrome). Foi criado por Ryan Dahl em 2009, e seu desenvolvimento é mantido pela fundação Node.js em parceria com a Linux Foundation.
O Node roda em uma JavaScript V8 VM. Mas espere, JavaScript no servidor? Isso, você leu certo. JavaScript no lado do servidor pode ser um conceito novo para todos que trabalharam exclusivamente com o JavaScript no lado do cliente, mas a idéia em sí não é tão absurda – porque não usar a mesma linguagem de programação no cliente que você usa no servidor?
O que é V8? O motor JavaScript V8 é o motor que a Google usa com seu navegador Chrome. Poucas pessoas pensam sobre o que realmente acontece com o JavaScript no lado do cliente. Bem, a engine JavaScript realmente interpreta o código e o executa. Com o V8 a Google criou um ultra-rápido interpretador escrito em C++, com um outro aspecto único: você pode baixar a engine e incorporá-la em qualquer aplicação desejada. Isso não está restrito em rodar em um navegador. Então Node atualmente usa o motor JavaScript V8 escrito pela Google e propõe que seja usado no servidor.
Express.js , ou simplesmente Express , é uma estrutura de aplicativo da web para o Node.js, lançada como software livre e de código aberto sob a licença MIT . Ele é projetado para construir aplicativos da Web e APIs . Ele foi chamado de framework de servidores padrão de fato para o Node.js.
O autor original, TJ Holowaychuk , descreveu-o como um servidor inspirado no Sinatra , o que significa que é relativamente mínimo com muitos recursos disponíveis como plugins. Express é o componente backend da pilha MEAN , junto com o software de banco de dados MongoDB e a estrutura de frontend Angular.
Para instalar:
npm i nodemon –g
Esse módulo é um utilitário que irá monitorar todas as alterações nos arquivos de sua aplicação e reiniciar automaticamente o servidor quando for necessário.
O Nodemon é um utilitário que monitora quaisquer alterações em sua origem e reinicia automaticamente seu servidor. Perfeito para o desenvolvimento. Instale-o usando npm .
Basta usar em nodemonvez de nodeexecutar seu código e, agora, seu processo será reiniciado automaticamente quando o código for alterado. Para instalar, obtenha node.js e , a partir do seu terminal, execute:
Características:
• Reinício automático da aplicação.
• Detecta extensão de arquivo padrão para monitorar.
• Suporte padrão para node & coffeescript, mas fácil de executar qualquer executável (como python, make, etc).
• Ignorando arquivos ou diretórios específicos.
• Assista diretórios específicos.
• Funciona com aplicativos de servidor ou utilitários de execução única e REPLs.
• Necessário em aplicativos de nó.
Código aberto e disponível no github
Para instalar:
npm i mongoose -g
Mongoose é uma biblioteca do Nodejs que proporciona uma solução baseada em esquemas para modelar os dados da sua aplicação. Ele possui sistema de conversão de tipos, validação, criação de consultas e hooks para lógica de negócios.
Mongoose fornece um mapeamento de objetos do MongoDB similar ao ORM (Object Relational Mapping), ou ODM (Object Data Mapping) no caso do Mongoose. Isso significa que o Mongoose traduz os dados do banco de dados para objetos JavaScript para que possam ser utilizados por sua aplicação.
O express.bodyParser() é uma função que facilita a construção de objetos JSON apartir de uma submissão de dados de um formulário html, ele simplesmente monta um objeto apartir dos valores do campo name, em que o campo name cria um objeto e atributos e o campo value insere valores nesses objetos.
Uma classe é uma forma de definir um tipo de dado em uma linguagem orientada a objeto. Ela é formada por dados e comportamentos.
Para definir os dados são utilizados os atributos, e para definir o comportamento são utilizados métodos. Depois que uma classe é definida podem ser criados diferentes objetos que utilizam a classe. A Listagem 1 mostra a definição da classe Empresa, que tem os atributos nome, endereço, CNPJ, data de fundação, faturamento, e também o método imprimir, que apenas mostra os dados da empresa.
O conceito do encapsulamento consiste em “esconder” os atributos da classe de quem for utilizá-la. Isso se deve por dois motivos principais.
Um é para que alguém que for usar a classe não a use de forma errada como, por exemplo, em uma classe que tem um método de divisão entre dois atributos da classe - se o programador java não conhecer a implementação interna da classe, ele pode colocar o valor zero no atributo do dividendo, mas se a classe estiver corretamente encapsulada podemos impedir que o programador faça isso.
A associação de classes indica quando uma classe tem um tipo de relacionamento "tem um" com outra classe como, por exemplo, uma pessoa tem um carro e isso indica que a classe Pessoa tem uma associação com a classe Carro. Esse tipo de relacionamento entre classes é importante, porque define como as classes interagem entre elas nas aplicações.
A herança é um tipo de relacionamento que define que uma classe "é um" de outra classe como, por exemplo, a classe Funcionario que é uma Pessoa, assim um Funcionário tem um relacionamento de herança com a classe Pessoa. Em algumas linguagens, como C, é possível fazer herança múltipla, isto é, uma classe pode herdar de diversas outras classes, mas em Java isso não é permitido, pois cada classe pode herdar de apenas outra classe.
Herança é um princípio de orientação a objetos, que permite que classes compartilhem atributos e métodos, através de "heranças". Ela é usada na intenção de reaproveitar código ou comportamento generalizado ou especializar operações ou atributos. O conceito de herança de várias classes é conhecido como herança múltipla. Como exemplo pode-se observar as classes 'aluno' e 'professor', onde ambas possuem atributos como nome, endereço e telefone. Nesse caso pode-se criar uma nova classe chamada por exemplo, 'pessoa', que contenha as semelhanças entre as duas classes, fazendo com que aluno e professor herdem as características de pessoa, desta maneira pode- se dizer que aluno e professor são subclasses de pessoa. Também podemos dizer que uma classe pode ser abstrata(abstract) ou seja ela não pode ter uma instância, ela apenas "empresta" seus atributos e metódos como molde para novas classes.
O princípio da interface é um alicerce da programação modular que, por sua vez, é precursora e parte da programação orientada a objeto. Na programação orientada a objeto, a interface de um objeto consiste de um conjunto de métodos que um objeto deve suportar. É importante notar que as variáveis de instância não fazem parte da interface de um objeto pois devem ser acessadas somente pelos "métodos de acesso". Historicamente, as interfaces são derivadas dos arquivos de cabeçalho da Linguagem C (normalmente arquivos com extensão ".h") que separam o contexto sintático de um módulo (ou protótipos de funções) da sua implementação.
Algumas linguagens de programação orientadas a objeto exigem que a interface do objeto seja especificada de forma separada da implementação do objeto, enquanto outras não fazem esta exigência. Por exemplo, em linguagens de programação como Objective-C, a classe do objeto define a sua interface e é declarada em um arquivo de cabeçalho (header em inglês) e, por outro lado, a implementação da classe é mantida em um arquivo chamado de "arquivo fonte". Devido à tipagem dinâmica existente na Objective-C, que permite o envio de mensagens para qualquer objeto, a interface de uma classe é importante para determinar para quais métodos um objeto de uma classe responde.
A linguagem de programação Java, que recebeu influência da Objective-C, utiliza outra abordagem para o conceito de interface, assim como outras linguagens orientadas a objeto, onde a interface especifica um conjunto de métodos ou funcionalidades comuns a um conjunto de classes. Ver interface na linguagem Java.
Em arquitetura de software há muitas camadas entre o hardware e o usuário final. Cada uma pode ser dita como tendo um front-end e um back-end. O front-end é uma abstração, simplificando o componente subjacente pelo fornecimento de uma interface amigável, como por um exemplo um navegador de Internet, ou um formulário para um determinado usuário.
Em projetos de software, por exemplo, a arquitetura modelo-visão-controlador fornece o -end e o back-end para o banco de dados, o usuário e para os componentes de processamento. A separação de sistemas de software em front-end e back-end simplifica o desenvolvimento e separa a manutenção. Uma regra de ouro é que o lado frontal (ou "cliente") é qualquer componente manipulado pelo usuário. O código do lado do servidor (ou back-end) reside no servidor. A confusão surge quando alguém tem que fazer edições na parte frontal para arquivos do lado servidor. Muitos projetistas HTML, por exemplo, não precisam estar no servidor quando eles estão desenvolvendo o HTML. Reciprocamente, engenheiros do lado servidor, por definição, nunca estão em qualquer coisa, mas num servidor. Considera-se os dois para, finalmente, fazer um site web funcional e interativo.
Para subsistemas de computação maiores, um gerenciador de arquivos gráfico é um front-end para o sistema de arquivos do computador e um shell faz a interface com o sistema operacional. O front-endreveste o usuário e o back-end executa os programas do sistema operacional em resposta.
Arquitetura Modelo-Visão-Controlador (do inglês: Model-View-Controller - MVC) é um padrão de arquitetura de software (não confundir com design pattern) que separa a representação da informação da interação do usuário com ela. Normalmente usado para o desenvolvimento de interfaces de usuárioque divide uma aplicação em três partes interconectadas. Isto é feito para separar representações de informação internas dos modos como a informação é apresentada para e aceita pelo usuário. O padrão de projeto MVC separa estes componentes maiores possibilitando a reutilização de código e desenvolvimento paralelo de maneira eficiente.
O modelo (model) consiste nos dados da aplicação, regras de negócios, lógica e funções. Uma visão (view) pode ser qualquer saída de represenção dos dados, como uma tabela ou um diagrama. É possível ter várias visões do mesmo dado, como um gráfico de barras para gerenciamento e uma visão tabular para contadores. O controlador (controller) faz a mediação da entrada, convertendo-a em comandos para o modelo ou visão. As ideias centrais por trás do MVC são a reusabilidade de código e separação de conceitos.
Tradicionalmente usado para interfaces gráficas de usuário (GUIs), esta arquitetura tornou-se popular para projetar aplicações web e até mesmo para aplicações móveis, para desktop e para outros clientes. Linguagens de programação populares como Java, C#, Ruby, PHP e outras possuem frameworks MVC populares que são atualmente usados no desenvolvimentos de aplicações web.
Camada de apresentação ou visualização (View) - Não se dedica em saber como o conhecimento foi retirado ou de onde ela foi obtida, apenas mostra a referência. Segundo Gamma et al (2006), ”A abordagem MVC separa a View e Model por meio de um protocolo inserção/notificação (subscribe/notify). Uma View deve garantir que sua expressão reflita o estado do Model. Sempre que os dados do Model mudam, o Model altera as Views que dependem dele. Em resposta, cada View tem a oportunidade de modificar-se”. Adiciona os elementos de exibição ao usuário : HTML, ASP, XML, Applets. É a camada de interface com o usuário. É utilizada para receber a entrada de dados e apresentar visualmente o resultado.
Camada de lógica da aplicação (Model) - É o coração da execução, responsável por tudo que a aplicação vai fazer a partir dos comandos da camada de controle em um ou mais elementos de dados, respondendo a perguntas sobre o sua condição e a instruções para mudá-las. O modelo sabe o que o aplicativo quer fazer e é a principal estrutura computacional da arquitetura, pois é ele quem modela o problema que está se tentando resolver. Modela os dados e o comportamento por atrás do processo de negócios. Se preocupa apenas com o armazenamento, manipulação e geração de dados. É um encapsulamento de dados e de comportamento independente da apresentação.
Camada de controle (Control) - É responsável por interpretar as ações de entrada através do mouse e teclado realizadas pelo usuário. O Controle (Controller) envia essas ações para o Modelo (Model) e para a janela de visualização (View) onde serão realizadas as operações necessárias.
Um array é uma estrutura de dados homogênea que mantém uma série de elementos de dados de mesmo tipo. Pode-se acessar os elementos individuais armazenados no array por meio de uma posição de índice associada, geralmente numérica.
No geral, os arrays possuem tamanho fixo, ou seja, número de posições definida; em algumas linguagens de programação, existem estruturas de arrays que possuem tamanho variável. Vamos estudar aqui os arrays tradicionais, de tamanho especificado.
Classificação dos arrays
Os arrays são classificados de acordo com a sua dimensão de armazenamento de dados, como segue:
Uma matriz é uma coleção de variáveis de mesmo tipo, acessíveis com um único nome e armazenados contiguamente na memória. A individualização de cada variável de um vetor é feita através do uso de índices.
Os Vetores são matrizes de uma só dimensão.
Um vetor é um array unidimensional, ou seja, de uma única dimensão; é análogo a uma linha única de dados em uma planilha ou tabela. A figura a seguir ilustra a estrutura interna de um vetor de quatro posições, que permite portanto armazenar até quatro dados, de nome Notas.
No geral a contagem das posições se inicia em zero (0), de modo que a primeira posição do vetor será a posição 0, a segunda posição será 1, e assim por diante; a última posição do vetor será a de número n – 1, onde n é o número total de posições disponíveis (tamanho do array). Assim, em um vetor de 4 posições a última posição será 4 – 1 = 3. As posições em um vetor são sempre indicadas pelo número da posição entre colchetes [ ].
Declaração de vetores
Podemos declarar um vetor em português estruturado usando a seguinte sintaxe:
nomeVetor: vetor [i..f] de Tipo_Dados
Onde:
Declaração de Matrizes
int Vetor[5]; // declara um vetor de 5 posições
int Matriz[5][3]; // declara uma matriz de 5 linhas e 3 colunas
Acesso aos elementos do vetor
Para acessar os elementos de um vetor usa-se índices. O índice define a posição da variável dentro do vetor. Em todos os vetores tem o primeiro elemento na posição 0(zero). Assim, se tomarmos "K" como sendo o tamanho do vetor a última posição é a de índice "K-1"
Vetor[0] = 4; // Coloca 4 na primeira posição de "Vetor"
Vetor[4] = 8; // Coloca 8 na última posição de "Vetor"
Exemplos com Vetores
int Vetor[5]; // declara um vetor de 5 posições
int Matriz[5][3]; // declara uma matriz de 5 linhas e 3 colunas
Vetor[0] = 9; // coloca 9 na primeira posição do vetor
Vetor[4] = 30 // coloca 30 na última posição do vetor
Matriz[0][1] = 15; // coloca 15 na célula que está na primeira linha
// e na segunda coluna da matriz
No desenvolvimento de uma aplicação, é muito comum utilizarmos estruturas condicionais como, por exemplo, ifs e elses ou switch case. Porém, em algum momento da nossa vida, provavelmente, um desses testes que realizamos é tão simples que retorna um valor para apenas duas possibilidades.
Por exemplo, suponhamos que precisamos criar uma funcionalidade para gerar uma bonificação e a regra para essa funcionalidade é a seguinte:
Uma solução seria utilizar um if e else como já conhecemos, como por exemplo no Java:
double salario = 1000;
double bonus = 0.0;
if (salario > 1000) {
bonus = salario * 0.10;
} else {
bonus = salario * 0.15;
}
System.out.println(bonus);
Nesse exemplo o resultado é 150.0 pois o salário é menor que R$ 1000.0, ou seja, bônus de 15%.
Entretanto, perceba que o que estamos fazendo é apenas um teste bem básico que tem apenas uma única linha de código dentro do if ou do else. Será que não existe uma maneira mais simples de resolver o mesmo problema?
Em um cenário similar a esse, podemos também utilizar o operador ternário que funciona com o mesmo conceito do if e else, porém, a única diferença é que precisamos devolver um valor após o teste estritamente em uma única linha!
double salario = 1000;
double bonus = salario * (salario > 1000 ? 0.10 : 0.15);
System.out.println(bonus);
Com esse código acima temos o mesmo resultado de antes, ou seja, 150.0. Mas como funciona esse operador ternário? A estrutura de um operador ternário é compreendida da seguinte forma:
Condição? valor se for verdareiro : valor se for falso
Portanto, inicialmente temos um teste (podemos adicionar um teste qualquer), ou seja, qualquer teste devolve um valor booleano, então, definimos o primeiro parâmetro que é justamente o valor que será retornado caso o teste for verdadeiro e o segundo que será retornado caso for falso!
Justamente pelo fato de realizar essas 3 operações, o chamamos de operador ternário. Mas isso é só em Java? Não! Diversas linguagens implementam esse mesmo recurso!
Vejamos alguns exemplos:
JavaScript:
var salario = 1000;
var bonus = salario * (salario > 1000 ? 0.10 : 0.15);
Angular (comumente referido como "Angular 2+" ou "Angular 2") é uma plataforma de aplicações web de código-fonte aberto e front-end baseado em TypeScript liderado pela Equipe Angular do Google e por uma comunidade de indivíduos e corporações. Angular é uma reescrita completa do AngularJS, feito pela mesma equipe que o construiu.
Arquitetura de uma aplicação Angular. Os principais blocos são módulos, componentes, templates, metadados, enlace de dados, directivas, serviços e injeção de dependência.Angular foi uma base de reescrita do AngularJS.
Originalmente, a reescrita do AngularJS foi chamado de "Angular 2" pela equipe, mas isto levou à confusão entre os desenvolvedores. Para esclarecer, a equipe anunciou que termos separados devem ser usados para cada Framework, com "AngularJS", referindo-se a 1.X versões e "Angular" sem o "JS", referindo-se às versões à partir da 2 até a última.
A versão 2.0
O Angular 2.0 foi anunciado no ng-Europe conference 22-23 de setembro de 2014. As mudanças drásticas na versão 2.0 criou uma considerável controvérsia entre os desenvolvedores. Em 30 de abril de 2015, os desenvolvedores Angular anunciaram que o Angular 2 foi transformado de Alfa a Developer Preview. O Angular 2 mudou-se para o Beta em dezembro de 2015,e a primeira versão foi publicada em Maio de 2016 A versão final foi lançada em 14 de setembro de 2016.
Versão 4.0
Em 13 de dezembro de 2016 Angular 4 foi anunciado, ignorando o 3 para evitar uma confusão devido ao desalinhamento da versão do pacote do roteador que já foi distribuído como v3.3.0. A versão final foi lançada em 23 de Março de 2017. O Angular 4 é compatível com o Angular 2.
O Angular versão 4.3 é uma versão menor, o que significa que ele contém alterações que não são de última hora e que é uma atualização pequena para 4.x.x.
Recursos na versão 4.3
Introdução de HttpClient, uma biblioteca menor, mais poderosa, e mais fácil de usar, para fazer Solicitações HTTP.
Novo roteador ciclo de vida de eventos para Guardas e Resoluções. Quatro novos eventos: GuardsCheckStart, GuardsCheckEnd, ResolveStart, ResolveEnd juntam-se ao conjunto existente de ciclo de vida, tais como a NavigationStart. Condicionalmente desativa animações.
Versão 5.0
Angular 5 foi lançado em 1 de novembro de 2017. Os principais aprimoramentos Angular 5 incluem suporte para web apps progressivos, uma compilação otimizadora e melhorias relacionadas ao Material Design.
Versão 6.0
O lançamento da sexta versão do Angular ocorreu no dia quatro de Maio de 2018. Esta versão teve um foco menor na base do framework, e maior na cadeia de ferramentas e em como tornar mais fácil e rápida a migração com Angular nas atualizações futuras, como os comandos da CLI (Interface de Linha de Comando): ng update, ng add, Angular Elements, Componentes Angular Material + CDK, Componentes Iniciais Angular Material, CLI Workspaces, Suporte a biblioteca, Provedores de Árvore Shakable, Melhoramentos no desempenho de animações, e atualização do RxJS para a versão 6.
Versão 7.0
A sétima versão do Angular foi lançada no dia dezoito de Outubro de 2018. Atualizações relacionadas ao desempenho de aplicativos, Angular Material & CDK, Rolagem Virtual, Melhor acessibilidade do elemento de formulário select (também conhecido por combobox ou dropdownlist), agora suporta Content Projection usando o padrão web para elementos personalizados, e atualizações de dependência em relação ao Typescript 3.1, RxJS 6.3, Node 10 (ainda suportando Node 8).
Versão 7.1
O lançamento do Angular 7 ocorreu em novembro de 2018 e está disponível
Versão 8.0
O lançamento da mais nova versão do Angular ocorreu em maio de 2019 e conta com algumas melhorias no funcionamento dos formulários reativos, melhoria na sintaxe para declaração de rotas lazy-loading e a esperada disponibilização do compilador Ivy, que nesta versão ainda está em preview e precisa ser habilitado, mas não é recomendado que se utilize em produção.
Cada versão está prevista para ser compatível com a versão anterior. O Google se comprometeu a fazer atualizações duas vezes por ano.
Versão 9.0
O Angular 9 foi lançado em 6 de fevereiro de 2020. A versão 9 move todos os aplicativos para usar o compilador Angular Ivy por padrão. O Angular foi atualizado para funcionar com TypeScript 3.6 e 3.7. Além de centenas de correções de bugs, o compilador e o tempo de execução Ivy oferecem inúmeras vantagens:
Versão 10
O Angular 10 foi lançado em 24 de junho de 2020:
Versão 11
Versão 12
Angular 13
Angular 14
Angular 15
Angular 16
Angular 17
.
.
.
Essa estrutura é bastante organizada e escalável, permitindo a adição de novos componentes, serviços, módulos e recursos de forma eficiente. Também facilita a colaboração em equipe e a manutenção do código ao longo do tempo.
.
.
.
TypeScript é um superconjunto de JavaScript desenvolvido pela Microsoft que adiciona tipagem e alguns outros recursos a linguagem. Anders Hejlsberg, arquiteto da linguagem C# e criador das linguagens Delphi e Turbo Pascal, trabalhou no desenvolvimento do TypeScript. A linguagem pode ser usada para desenvolver aplicações JavaScript no lado cliente e lado servidor (Node.js).
Foi considerada pelo público a 4ª linguagem "mais amada", de acordo com uma pesquisa conduzida pelo site Stack Overflow em 2018, e está entre as 15 linguagens mais populares, de acordo com uma pesquisa conduzida pela RedMonk
TypeScript é um superconjunto de JavaScript
Isso significa que o TypeScript estende JavaScript com funcionalidade extra que não está presente na versão atual do JavaScript suportada pela maioria dos navegadores. Então, quais são esses recursos?
Se você estiver familiarizado com linguagens como Java ou C #, provavelmente sabe que cada variável requer um tipo e esse tipo deve ser declarado antecipadamente . JavaScript é uma linguagem fracamente tipada ou digitada dinamicamente. As variáveis em JavaScript não estão diretamente associadas a nenhum tipo de valor específico, e qualquer variável pode ser atribuída (e reatribuída) a todos os tipos de valores:
var foo = 42; // foo is now a Number
var foo = 'bar'; // foo is now a String
var foo = true; // foo is now a Boolean
Em uma linguagem fracamente tipada, o tipo de um valor depende de como ele é usado . Por exemplo, se eu puder passar uma string para o operador de adição e ela será automaticamente interpretada como um número ou causará um erro se o conteúdo da string não puder ser traduzido em um número . Da mesma forma, posso concatenar cadeias e números ou usar strings como booleanos, etc.
Em uma linguagem fortemente tipada, uma variável tem um tipo e esse tipo não pode mudar . O que você pode fazer com uma variável depende do seu tipo. Se tentarmos compilar o código acima no TypeScript, obteremos o erro:
[ts] Subsequent variable declarations must have the same type.
Variable 'foo' must be of type 'number', but here has type 'boolean'.
A vantagem de uma linguagem fortemente tipada é que você é forçado a tornar explícito o comportamento do seu programa . Se você quiser adicionar um número e uma string ao seu código, você deve traduzir a string em um número a ser usado como um operando do operador de adição. Isso torna o código mais fácil de entender porque não há comportamento (ou menos) oculto . Isso também torna seu código mais detalhado.
Lembrar:
A tipificação forte é opcional no TypeScript, mas o uso desse recurso torna seu aplicativo mais previsível e facilita a depuração, portanto, você deve definitivamente usá-lo.
A programação orientada a objetos (OOP) é um conceito antigo usado por vários idiomas, como Java ou C #, para ajudar o desenvolvedor a associar dados e métodos em um "objeto". Em OOPobjeto são criados e são capazes de interagir uns com os outros usando os métodos de enfrentamento público um do outro. JavaScript em si não é uma linguagem orientada a objetos na maneira que C ++, C # ou Java são. O TypeScript, por outro lado, pode ser tratado como uma linguagem orientada a objetos por causa das construções de linguagem introduzidas sobre os fechamentos de JavaScript.
O TypeScript traz muitos recursos orientados a objetos que perdemos no JavaScript por um longo tempo. Temos conceitos explícitos de:
Deixe-me explicar primeiro o que run-time error é como este é um caso comum. Estamos falando sobre run-time error quando enfrentamos qualquer problema ao usar nosso aplicativo. Em outras palavras - se você cometer um erro ao criar seu site e escrever algum código, você o verá apenas enquanto estiver usando o aplicativo / site. Por exemplo, se você cometer um erro de digitação em um arquivo de página da Web, o console do seu navegador mostrará um erro quando você carregar essa página.
Devido à fraca tipagem em JavaScript, muitas vezes acontece que tentamos realizar operações em uma variável com um tipo diferente. Se a nossa lógica de aplicativo for complexa, talvez não percebamos que estamos tentando atribuir elementos de um tipo diferente uns aos outros. Em JavaScript, só saberemos sobre o erro quando alguém acionar um código e ele falhar . Por outro lado, o TypeScript pode nos fornecer erros de tempo de compilação, o que significa que ele pode detectar erros ao compilar código para JavaScript e corrigi-lo antes de implantar na produção. Claro que não vai pegá-los todos, mas ainda muito.
O TypeScript fornece aos desenvolvedores conceitos orientados a objeto e compila a verificação do tipo de tempo em cima do JavaScript, o que ajuda a escrever código mais estruturado, sustentável e robusto. O TypeScript introduz alguns dos termos orientados a objetos padrão, como Classes, Interfaces, Module e Variables, que no final são convertidos em várias formas diferentes de JavaScript. A estrutura de código para um arquivo TypeScript típico é mostrada abaixo.
O módulo é como um namespace no mundo .NET e pode conter classes e interfaces. Os módulos não possuem nenhum recurso próprio, eles apenas fornecem um contêiner que pode ser usado para estruturar o código de forma lógica. Olhe para o módulo apenas como um contêiner de entidade lógica / comercial.
Interfaces são exatamente como interfaces no .NET que fornecem um contrato para as classes implementarem. O TypeScript ajuda a fornecer verificação de erros de tempo de compilação para as classes que implementam essas interfaces. Se todos os métodos não foram implementados corretamente (incluindo a assinatura do método), o TypeScript sinaliza aqueles em tempo de design, bem como o tempo de compilação. Coisa interessante sobre Interfaces é que eles não existem em JavaScript e, portanto, quando compilamos um arquivo TypeScript em JavaScript, as Interfaces são omitidas.
O conceito de Classes é novamente muito semelhante ao mundo .NET / Java. Classes contém variáveis, propriedades e métodos que formam uma entidade lógica. O TypeScript também permite definir o escopo da variável e funções com palavras-chave como “ private” e “ public”, embora esse escopo não tenha qualquer efeito sobre o JavaScript gerado.
Funções são métodos em que a lógica é implementada. O TypeScript fornece suporte de tempo de compilação para garantir que qualquer pessoa que chame a função mencionada concorde com o argumento de entrada e com o tipo de valor de retorno.
Variáveis são os campos definidos dentro de uma classe ou função. O TypeScript nos permite definir uma variável usando a palavra-chave “ var” e atribuir um tipo de dados a ela. Uma vez que um tipo de dado é atribuído, qualquer uso adicional da variável deve ser com o mesmo tipo de dados, caso contrário, o TypeScript gerará erro no design e no tempo de compilação. O TypeScript também é inteligente o suficiente para inferir o tipo de uma variável e depois tratá-la como esse tipo quando uma variável é declarada e inicializada. Nos casos em que o TypeScript não é capaz de inferir o tipo, ele atribuirá esse tipo de variável “ any”.
Tipos de TypeScript
O TypeScript fornece alguns tipos primitivos (mostrados abaixo), bem como um tipo dinâmico “ any”. " Any" É como " dynamic" palavra-chave em c # em que podemos atribuir qualquer tipo de valor para a variável. O TypeScript não sinaliza erros de tipo para variáveis do tipo “ any”.
No TypeScript, definimos uma variável com um tipo apenas acrescentando o nome da variável com dois-pontos, seguido do nome do tipo, como mostrado no exemplo abaixo.
var num: number = 30; //variable num is of type number
Abaixo está a lista de tipos primitivos disponíveis no TypeScript:
Classes
Classes TypeScript são uma unidade básica de abstração muito semelhante às classes C # / Java. No TypeScript, uma classe pode ser definida com a palavra-chave “ class” seguida do nome da classe. Classes TypeScript podem conter construtor, campos, propriedades e funções. O TypeScript permite que os desenvolvedores definam o escopo da variável dentro das classes como “ public” ou “ private”. É importante notar que as palavras-chave “ public/ private” só estão disponíveis no TypeScript, uma vez convertido para JavaScript, não há como distinguir entre os dois e ambos podem ser chamados. O TypeScript define um construtor usando a palavra-chave " constructor".
Exemplo em Typescript:
class Student {
private firstName: string;
private lastName: string;
yearOfBirth: number; //Public scope by default
schoolName: string;
city: string;
//Constructor
constructor(firstName: string, lastName: string, schoolName: string,
city: string, yearOfBirth: number) {
this.firstName = firstName;
this.lastName = lastName;
this.yearOfBirth = yearOfBirth;
this.city = city;
this.schoolName = schoolName;
}
//Function
age() {
return 2014 - this.yearOfBirth;
}
//Function
printStudentFullName(): void {
alert(this.lastName + ',' + this.firstName);
}
}
Exemplo em Javascript:
var Student = (function () {
//Constructor
function Student(firstName, lastName, schoolName, city, yearOfBirth){
this.firstName = firstName;
this.lastName = lastName;
this.yearOfBirth = yearOfBirth;
this.city = city;
this.schoolName = schoolName;
}
//Function
Student.prototype.age = function () {
return 2014 - this.yearOfBirth;
};
//Function
Student.prototype.printStudentFullName = function () {
alert(this.lastName + ',' + this.firstName);
};
return Student;
})();
No construtor acima definido em TypeScript, temos poucas variáveis de entrada que são então mapeadas para variáveis locais dentro de uma classe, podemos modificar esse construtor para implementar declaração e mapeamento de variáveis implícitas definindo o escopo juntamente com o nome da variável na definição do construtor, como mostrado abaixo:
constructor(private firstName: string,
private lastName: string, public schoolName: string,
public yearOfBirth: number) {}
No caso acima, as variáveis agora são definidas e declaradas apenas dentro do argumento do construtor. O escopo mencionado junto com o argumento se torna o escopo da variável para essa classe.
Para consumir a classe, o comportamento é semelhante ao C #, onde usamos a new palavra-chave “ ” para inicializar o objeto de classe, passar quaisquer parâmetros se o construtor exigir e, em seguida, chamar as funções ou acessar as publicvariáveis da classe.
var student = new Student('Tom', 'Hanks', 'World Acting School',1950);
var age = student.age();
var fullName = student.printStudentFullName();
var schoolName = student.schoolName;
Interfaces
O TypeScript oferece suporte para Interfaces para usá-los como um contrato para classes semelhantes a C #. Para declarar uma interface, usamos a palavra-chave “ interface” seguida do nome da interface. O importante a saber sobre interfaces é que, quando compilado em JavaScript, o código da interface é ignorado e não há JavaScript correspondente gerado.
interface IStudent {
yearOfBirth: number;
age : () => number;
}
As classes implementam interfaces usando a palavra-chave “ implement” seguida do nome da interface. Como em C #, as classes podem implementar várias interfaces e o TypeScript faz uma verificação de tempo de design para garantir que a classe esteja implementando todos os métodos dessa interface.
class Student implements IStudent
Aqui, a Student classe agora terá que implementar o agemétodo “ ” e definir a propriedade ” yearOfBirth”. Caso contrário, o TypeScript mostrará o erro de tempo de projeto com o erro mencionando qual propriedade / método não foi implementada na classe.
Herança
Ter classes e interface significa que o TypeScript também suporta herança, que é um recurso muito poderoso e alinha a escrita do código do lado do cliente com a maneira como escrevemos código C #. Usando herança, podemos estender classes, implementar e estender interfaces e escrever código que seja reconhecido de perto com OOPs. Em TypeScript, quando estendemos uma classe base na classe filha, usamos a palavra-chave “ super” para chamar o construtor da classe base ou até mesmo os publicmétodos da classe base.
Para estender uma classe no TypeScript, usamos “ extend” palavra-chave após o nome da classe e, em seguida, seguimos pela classe pela qual precisamos estender. Também podemos herdar interfaces em outras interfaces.
//Interface
interface IStudent {
yearOfBirth: number;
age : () => number;
}
//Base Class
class College {
constructor(public name: string, public city: string) {
}
public Address(streetName: string) {
return ('College Name:' + this.name + ' City: ' + this.city
+ ' Street Name: ' + streetName);
}
}
//Child Class implements IStudent and inherits from College
class Student extends College implements IStudent {
firstName: string;
lastName: string;
yearOfBirth: number;
//private _college: College;
//Constructor
constructor(firstName: string, lastName: string, name: string,
city: string, yearOfBirth: number) {
super(name, city);
this.firstName = firstName;
this.lastName = lastName;
this.yearOfBirth = yearOfBirth;
}
age () {
return 2014 - this.yearOfBirth;
}
CollegeDetails() {
var y = super.Address('Maple Street');
alert(y);
}
printDetails(): void {
alert(this.firstName + ' ' + this.lastName
+ ' College is: ' + this.name);
}
}
No TypeScript, também podemos definir qualquer parâmetro com um valor padrão e, ao chamar essa função, não precisamos passar o valor desses parâmetros. Se não passarmos o valor, então a função recebe o valor padrão atribuído, senão o valor passado na chamada de função é obtido como mostrado no exemplo abaixo:
constructor(private firstName: string, private lastName: string,
public schoolName: string,
public yearOfBirth: number = 1990){}
No exemplo acima, atribuímos um valor opcional ao yearOfBirthcampo “ ” e se no caso a função de chamada não passar nenhum valor para este campo, o construtor irá inicializá-lo com 1990.
Similar é o caso dos parâmetros Opcionais, podemos definir um parâmetro adicionando um “ ?” após o nome do parâmetro. Nesse caso, quando a função é chamada, não precisamos passar o valor para esse parâmetro.
Subject(subjectList?: string[]) {
if (subjectList == null) {
alert('Oh, You have not subscribed to any course');
}
}
Aqui, se chamarmos o método de assunto sem passar nenhum valor de parâmetro, o TypeScript não mostrará nenhum erro.
Os operadores aritméticos são aqueles que nós estudamos na escola, aquelas funções básicas de somar, subtrair, multiplicar e dividir. Utilizando esses operadores nós podemos criar operações matemática com valores numéricos.
Abaixo você tem uma lista com os operadores que nós podemos utilizar com JavaScript:
Adição (+)
Nós utilizamos esse operador para somar valores numéricos:
var num1 = 13;
var num2 = 7;
console.log(num1 + num2); // resultado 20
Subtração (-)
Nós utilizamos esse operador para subtrair valores numéricos, retornando a diferença entre eles
var num1 = 20;
var num2 = 10;
console.log(num1 - num2); // resultado 10
Multiplicação (*)
Nós utilizamos esse operador multiplicar valores numéricos
var num1 = 3;
var num2 = 5;
console.log(num1 * num2); // resultado 15
Divisão (/)
Esse operador produz o quociente de seus operandos onde o operando da esquerda é o dividendo e o da direita é o divisor. Para que você possa relembrar, segue uma imagem abaixo retirada do Google.
var num1 = 20;
var num2 = 5;
console.log(num1 / num2); // resultado 4
Módulo (%)
Esse operador retorna o resto da divisão
var num1 = 3;
var num2 = 2;
console.log(num1 % num2); // resultado 1var num3 = 20;
var num4 = 5;
console.log(num3 % num4); // resultado 0var num5 = -1;
var num6 = 2
console.log(num5 % num6); // resultado -1
Exponenciação ()**
Esse operador retorna o valor do primeiro operando elevado ao segundo operado
var num1 = 3;
var num2 = 2;
console.log(num1 ** num2); // resultado 9
Incremento (++)
Esse operador incrementa um valor ao operando.
var num1 = 3;
console.log(num1++); // resultado 3var num2 = 1;
console.log(++num2); // resultado 2
Decremento (- -)
Esse operador decrementa (subtrai um de) seu operando e retorna um valor.
Esses são os operadores básicos para que possamos criar as nossas expressões do dia a dia.
Operadores lógicos são utilizados para comparar dois ou mais valores, retornando um valor Boolean. Abaixo você tem uma breve descrição deles:
Para ficar mais claro, veja abaixo alguns exemplos:
&& (and)
let num1: Number = 1;
let num2: Number = 3;
let valida = num1 == num2;
let valida2 = num1 > num2;
let valida3 = num1 < num2;
console.log(valida); //false
console.log(valida2); //false
console.log(valida3); //true
Analisado os exemplos acima nós temos:
let num1: Number = 1;
let num2: Number = 3;
let valida = num1 > 3 || num2 < 10;
let valida2 = num1 > 1 || num2 > 3;
let valida3 = num1 >= 1 || num2 >= 3;
console.log(valida); //true
console.log(valida2); //false
console.log(valida3); //true
Analisado o exemplo acima nós temos:
! (not)
let num1: Number = 1;
let num2: Number = 3;
let valida = num1 != num2;
console.log(valida); //true
Resultado:
num1 != num2: retorna true porque num1 e num2 são diferentes.
Em ciência da computação, programação funcional é um paradigma de programação que trata a computação como uma avaliação de funções matemáticas e que evita estados ou dados mutáveis. Ela enfatiza a aplicação de funções, em contraste da programação imperativa, que enfatiza mudanças no estado do programa. Enfatizando as expressões invés de comandos, as expressões são utilizados para calculo de valores com dados imutáveis.
Uma função, neste sentido, pode ter ou não ter parâmetros e um simples valor de retorno. Os parâmetros são os valores de entrada da função, e o valor de retorno é o resultado da função. A definição de uma função descreve como a função será avaliada em termos de outras funções. Por exemplo, a função é definida em termos de funções de exponenciação e adição. Do mesmo modo, a linguagem deve oferecer funções básicas que não requerem definições adicionais.
A Programação funcional trata a funções de forma em que estas possam ser passadas como parâmetro e valores para outras e funções e podendo ter o resultado armazenado em uma constante.
Linguagens de programação funcionais, especialmente as puramente funcionais, tem sido mais usadas academicamente que no desenvolvimento comercial de software. Entretanto, algumas linguagens notáveis usadas na indústri e no comércio incluem Erlang (aplicações concorrentes, R (estatística), Mathematica (matemática simbólica) J, K (análise financeira) e XSLT. Importantes influências na programação funcional foram o cálculo lambda, as linguagens de programação APL e Lisp, e mais recentemente ML, Haskell, OCaml, F# e Elixir.
A programação funcional é um paradigma que visa estruturar a construção de softwares seguindo o modelo de funções matemáticas, objetivando a imutabilidade dos dados e o acoplamento de funções, que resultam em benefícios como consistência tanto do código quanto dos dados – veremos os porquês no decorrer do artigo.
Semelhante a uma função matemática, um código funcional tem a sua saída condicionada exclusivamente à sua entrada, de modo que uma entrada garanta sempre a mesma saída após a execução do mesmo método, eliminando os chamados side-effects, que são as mudanças de estado ocasionadas por outros fatores que não dependam dos parâmetros do método.
1 Lista de códigos de status HTTP
2 1xx Informativa
2.1 100 Continuar
2.2 101 Mudando protocolos
2.3 102 Processamento (WebDAV) (RFC 2518)
2.4 122 Pedido-URI muito longo
3 200 Sucesso
3.1 201 Criado
3.2 202 Aceito
3.3 203 não-autorizado (desde HTTP/1.1)
3.4 204 Nenhum conteúdo
3.5 205 Reset
3.6 206 Conteúdo parcial
3.7 207-Status Multi (WebDAV) (RFC 4918)
4 3xx Redirecionamento
4.1 300 Múltipla escolha
4.2 301 Movido
4.3 302 Encontrado
4.4 303 Consulte Outros
4.5 304 Não modificado
4.6 305 Use Proxy (desde HTTP/1.1)
4.7 306 Proxy Switch
4.8 307 Redirecionamento temporário (desde HTTP/1.1)
4.9 308 Redirecionamento permanente (RFC 7538[2])
5 4xx Erro de cliente
5.1 400 Requisição inválida
5.2 401 Não autorizado
5.3 402 Pagamento necessário
5.4 403 Proibido
5.5 404 Não encontrado
5.6 405 Método não permitido
5.7 406 Não Aceitável
5.8 407 Autenticação de proxy necessária
5.9 408 Tempo de requisição esgotou (Timeout)
5.10 409 Conflito geral
5.11 410 Gone
5.12 411 comprimento necessário
5.13 412 Pré-condição falhou
5.14 413 Entidade de solicitação muito grande
5.15 414 Pedido-URI Too Long
5.16 415 Tipo de mídia não suportado
5.17 416 Solicitada de Faixa Não Satisfatória
5.18 417 Falha na expectativa
5.19 418 Eu sou um bule de chá
5.20 422 Entidade improcessável (WebDAV) (RFC 4918)
5.21 423 Fechado (WebDAV) (RFC 4918)
5.22 424 Falha de Dependência (WebDAV) (RFC 4918)
5.23 425 coleção não ordenada (RFC 3648)
5.24 426 Upgrade Obrigatório (RFC 2817)
5.25 450 bloqueados pelo Controle de Pais do Windows
5.26 499 cliente fechou Pedido (utilizado em ERPs/VPSA)
6 5xx outros erros
6.1 500 Erro interno do servidor (Internal Server Error)
6.2 501 Não implementado (Not implemented)
6.3 502 Bad Gateway
6.4 503 Serviço indisponível (Service Unavailable)
6.5 504 Gateway Time-Out
6.6 505 HTTP Version not suppore
JSON (JavaScript Object Notation) é um modelo para armazenamento e transmissão de informações no formato texto. Apesar de muito simples, tem sido bastante utilizado por aplicações Web devido a sua capacidade de estruturar informações de uma forma bem mais compacta do que a conseguida pelo modelo XML, tornando mais rápido o parsing dessas informações. Isto explica o fato de o JSON ter sido adotado por empresas como Google e Yahoo, cujas aplicações precisam transmitir grandes volumes de dados.
A ideia utilizada pelo JSON para representar informações é simples: para cada valor representado, atribui-se um nome (ou rótulo) que descreve o seu significado. Esta sintaxe é derivada da forma utilizada pelo JavaScript para representar informações.
Um valor pode ser uma string entre aspas duplas, ou um número, ou verdadeiro ou falso ou nulo, ou um objeto ou uma matriz. Essas estruturas podem ser aninhadas.
Uma string é uma seqüência de zero ou mais caracteres Unicode, agrupados em aspas duplas, usando escapes de barra invertida. Um caractere é representado como uma única cadeia de caracteres. Uma string é muito parecida com uma string C ou Java.
Um número é muito parecido com um número C ou Java, exceto que os formatos octal e hexadecimal não são usados.
Um par nome/valor deve ser representado pelo nome entre aspas duplas, seguido de dois pontos, seguido do valor. Os valores podem possuir apenas 3 tipos básicos: numérico (inteiro ou real), booleano e string. As Listagens 2, 3, 4 e 5 apresentam exemplos. Observe que os valores do tipo string devem ser representados entre aspas.
Representando um número real
"altura": 1.72
Representando uma string
"site": “www.cotiinformatica.com.br”
Representando um número negativo
"temperatura": -2
Representando um valor booleano
"casado": true
A partir dos tipos básicos, é possível construir tipos complexos: array e objeto. Os arrays são delimitados por colchetes, com seus elementos separados entre vírgulas. As listagens 6 e 7 mostram exemplos.
Representando Array de Strings
[“RJ”, “SP”, “MG”, “ES”]
Representando Matriz de Inteiros
[
[1,5],
[-1,9],
[1000,0]
]
Os objetos são especificados entre chaves e podem ser compostos por múltiplos pares nome/valor, por arrays e também por outros objetos. Desta forma, um objeto JSON pode representar, virtualmente, qualquer tipo de informação! O exemplo da Listagem 8 mostra a representação dos dados de um filme.
Um objeto é um conjunto não ordenado de pares nome / valor. Um objeto começa com {(chave esquerda) e termina com} (chave direita). Cada nome é seguido por: (dois pontos) e os pares nome / valor são separados por (vírgula).
{
“titulo”: “JSON x XML”,
“resumo”: “o duelo de dois modelos de representação de informações”,
“ano”: 2012,
“genero”: [“aventura”, “ação”, “ficção”]
}
Uma matriz é uma coleção ordenada de valores. Um array começa com [(colchete esquerdo) e termina com] (colchete direito). Os valores são separados por (vírgula).
[
{
“titulo”: “JSON x XML”,
“resumo”: “o duelo de dois modelos de representação de informações”,
“ano”: 2012,
“genero”: [“aventura”, “ação”, “ficção”]
},
{
“titulo”: “JSON James”,
“resumo”: “a história de uma lenda do velho oeste”,
“ano”: 2012,
“genero”: [“western”]
}
]
A palavra-chave “null” deve ser utilizada para a representação de valores nulos.
Podemos entender o JSON como uma espécie de “concorrente” da XML na área de troca de informações.
Semelhanças:
• Os dois modelos representam informações no formato texto.
• Ambos possuem natureza auto-descritiva (ou seja, basta “bater o olho” em um arquivo JSON ou em um arquivo XML para entender o seu significado).
• Ambos são capazes de representar informação complexa, difícil de representar no formato tabular. Alguns exemplos: objetos compostos (objetos dentro de objetos), relações de hierarquia, atributos multivalorados, arrays, dados ausentes, etc.
• Ambos podem ser utilizados para transportar informações em aplicações AJAX.
• Ambos podem ser considerados padrões para representação de dados. XML é um padrão W3C, enquanto JSON foi formalizado na RFC 4627.
• Ambos são independentes de linguagem. Dados representados em XML e JSON podem ser acessados por qualquer linguagem de programação, através de API’s específicas.
Diferenças:
• JSON não é uma linguagem de marcação. Não possui tag de abertura e muito menos de fechamento!
• JSON representa as informações de forma mais compacta.
• JSON não permite a execução de instruções de processamento, algo possível em XML.
• JSON é tipicamente destinado para a troca de informações, enquanto XML possui mais aplicações. Por exemplo: nos dias atuais existem bancos de dados inteiros armazenados em XML e estruturados em SGBD’s XML nativo.
Ao acessar a home page oficial do JSON (www.json.org) você verá que existem parsers disponíveis para quase todas as linguagens: Delphi, PHP, Java, Matlab, C++, C#, etc.
No XML a coisa é bem mais fácil, pois existem duas API’s básicas para o parsing de informações: SAX e DOM. Ambas já são instaladas junto com o Java e, daí, basta utilizá-las. Adicionalmente, o princípio de funcionamento das API’s SAX e DOM é bastante conhecido pelos desenvolvedores: DOM importa o documento todo para a memória, criando uma árvore, enquanto o SAX percorre o arquivo sequencialmente disparando eventos, sem realizar a importação de informações para a memória.
O JSON parece ainda não ter atingido esse grau maturidade. Várias pessoas/empresas implementaram os seus próprios parsers, com diferentes princípios de funcionamento. Como ainda não há um padrão, fica difícil decidir qual utilizar!
Para converter um objeto Java para JSON, utiliza-se o método toJson. E para fazer ao contrário, ou seja, atribuir o conteúdo de um objeto Java a partir de uma string Json, utiliza-se fromJson.
Ter uma API pronta para começar o desenvolvimento do front-end da sua aplicação as vezes pode ser um problema. Com isso te apresento o JSON Server. JSON Server é uma biblioteca capaz de criar uma API Fake em 30 segundos e sem precisar escrever nenhuma linha de código.
REST vem de REpresentational State Transfer. É um estilo de arquitetura para projetar aplicações conectadas, usando os simples verbos HTTP para permitir a comunicação entre as máquinas. Assim, ao invés de usar uma URL para manipular informação do usuário, REST enviar uma requisição HTTP, como GET, POST, DELETE, etc., para uma URL manipular os dados.
APIs REST formam o backend de aplicações web e móveis. Ao criar aplicações, algumas vezes não temos APIs REST prontas para uso no durante o desenvolvimento. Para ver um app web ou móvel em ação, precisamos de um servidor que retorne dados JSON falsos. É aí que uma API REST falsa entra em ação. json-server provê a funcionalidade para configurar um servidor de API REST falso com mínimo de esforço.
https://www.npmjs.com/package/json-server
Digitar no terminal ou gitbash:
npm install -g json-server
Depois de instalado, inicializar o servidor com o arquivo desejado:
Importante digitar o comando no diretorio onde se encontra o arquivo json.
Exemplo:
json-server nome_do_arquivo.json
A injeção de dependência (DI) é um importante padrão de projeto de aplicativo. A Angular possui sua própria estrutura de DI, que é normalmente usada no projeto de aplicações angulares para aumentar sua eficiência e modularidade.
Dependências são serviços ou objetos que uma classe precisa para executar sua função. DI é um padrão de codificação em que uma classe pede dependências de fontes externas em vez de criá-las.
Em Angular, a estrutura de DI fornece dependências declaradas para uma classe quando essa classe é instanciada. Este guia explica como o DI funciona em Angular e como você o utiliza para tornar seus aplicativos flexíveis, eficientes e robustos, além de testáveis e de fácil manutenção.
A estrutura DI permite que você forneça dados para um componente de uma classe de serviço injetável , definida em seu próprio arquivo. Para demonstrar, criaremos uma classe de serviço injetável que forneça uma lista de heróis e registre essa classe como um provedor desse serviço.
Ter várias classes no mesmo arquivo pode ser confuso. Geralmente, recomendamos que você defina componentes e serviços em arquivos separados.
Se você combinar um componente e um serviço no mesmo arquivo, é importante definir primeiro o serviço e depois o componente. Se você definir o componente antes do serviço, obterá um erro de referência nulo em tempo de execução.
É possível definir o componente primeiro com a ajuda do forwardRef()método, conforme explicado neste post .
Você também pode usar referências avançadas para interromper dependências circulares. Veja um exemplo no DI Cookbook .
O decorador o marca como um serviço que pode ser injetado, mas o Angular não consegue injetá-lo em lugar algum até que você configure um injetor de dependência Angular com um provedor desse serviço.@Injectable()
O injetor é responsável por criar instâncias de serviço e injetá-las em classes como HeroListComponent. Você raramente cria um injetor angular sozinho. A Angular cria injetores para você enquanto executa o aplicativo, começando com o injetor de raiz que ele cria durante o processo de bootstrap .
Um provedor informa ao injetor como criar o serviço . Você deve configurar um injetor com um provedor antes que o injetor possa criar um serviço (ou fornecer qualquer outro tipo de dependência).
Um provedor pode ser a própria classe de serviço, para que o injetor possa usar newpara criar uma instância. Você também pode definir mais de uma classe para fornecer o mesmo serviço de maneiras diferentes e configurar diferentes injetores com provedores diferentes.
Os serviços são singletons no escopo de um injetor . Ou seja, há no máximo uma instância de um serviço em um determinado injetor.
Existe apenas um injetor de raiz para um aplicativo. Fornecer UserServiceno nível rootou AppModulesignifica que é registrado com o injetor de raiz. Há apenas uma UserServiceinstância em todo o aplicativo e cada classe que injeta UserServiceobtém essa instância de serviço, a menos que você configure outro provedor com um child injector.
O DI angular possui um sistema de injeção hierárquica , o que significa que os injetores aninhados podem criar suas próprias instâncias de serviço. Angular cria regularmente injetores aninhados. Sempre que Angular cria uma nova instância de um componente providersespecificado , também cria um novo injetor secundário para essa instância. Da mesma forma, quando um novo NgModule é carregado com preguiça em tempo de execução, o Angular pode criar um injetor para ele com seus próprios provedores.@Component()
Módulos filho e injetores de componentes são independentes uns dos outros e criam suas próprias instâncias separadas dos serviços fornecidos. Quando o Angular destrói um NgModule ou uma instância do componente, ele também destrói o injetor e as instâncias de serviço desse injetor.
Graças à herança do injetor , você ainda pode injetar serviços em todo o aplicativo nesses componentes. O injetor de um componente é um filho do injetor de seu componente pai e herda de todos os injetores ancestrais até o injetor de raiz do aplicativo . Angular pode injetar um serviço fornecido por qualquer injetor nessa linhagem.
Por exemplo, o Angular pode injetar HeroListComponenttanto
o HeroServicefornecido HeroComponentquanto o UserServicefornecido AppModule.
A maioria dos aplicativos front-end se comunica com os serviços de backend pelo protocolo HTTP. Navegadores modernos suportam duas APIs diferentes para fazer solicitações HTTP: a XMLHttpRequestinterface e a fetch()API.
O HttpClient oferece uma API HTTP de cliente simplificada para aplicativos Angulares que se apóia na interface exposta pelos navegadores. Os benefícios adicionais de incluir recursos de testabilidade, objetos de solicitação e resposta digitados, interceptação de solicitação e resposta, apis e tratamento simplificado de erros.
Antes de poder usar o HttpClient, você precisa importar o Angular HttpClientModule. A maioria dos aplicativos faz isso na raiz AppModule.
Este exemplo é tão simples que é tentador escrever o Http.get()interior do próprio componente e pular o serviço.
No entanto, o acesso a dados raramente fica tão simples. Você normalmente pós-processa os dados, adiciona manipulação de erros e talvez alguma lógica de repetição para lidar com a conectividade intermitente.
O componente rapidamente se torna confuso com minúcias de acesso a dados. O componente se torna mais difícil de entender, mais difícil de testar, e a lógica de acesso a dados não pode ser reutilizada ou padronizada.
É por isso que é uma prática recomendada separar a apresentação de dados do acesso a dados encapsulando o acesso a dados em um serviço separado e delegando a esse serviço no componente, mesmo em casos simples como este.
O que acontece se a solicitação falhar no servidor ou se uma conexão de rede ruim impedir que ela atinja o servidor? HttpClientretornará um objeto de erro em vez de uma resposta bem-sucedida.
Você poderia manipular no componente adicionando um segundo retorno de chamada ao .subscribe():
Detectar que um erro ocorreu é uma coisa. Interpretar esse erro e compor uma resposta amigável é um pouco mais envolvente.
Dois tipos de erros podem ocorrer. O back-end do servidor pode rejeitar a solicitação, retornando uma resposta HTTP com um código de status, como 404 ou 500. Essas são respostas de erro.
Ou algo pode dar errado no lado do cliente, como um erro de rede que impede que a solicitação seja concluída com êxito ou que uma exceção seja lançada em um operador RxJS. Esses erros produzem ErrorEventobjetos JavaScript.
A HttpClientcaptura de ambos os tipos de erros no seu HttpErrorResponsee você pode inspecionar essa resposta para descobrir o que realmente aconteceu.
Inspeção, interpretação e resolução de erros é algo que você deseja fazer no serviço , não no componente.
As seções anteriores deste guia se referiam a RxJS Observablese operadores como catchErrore retry. Você encontrará mais artefatos RxJS enquanto continua abaixo.
RxJS é uma biblioteca para composição de código assíncrono e baseado em retorno de chamada em um estilo funcional e reativo . Muitas APIs angulares, incluindo HttpClient, produzem e consomem RxJS Observables.
O próprio RxJS está fora do escopo deste guia. Você encontrará muitos recursos de aprendizado na web. Enquanto você pode conviver com um mínimo de conhecimento RxJS, você vai querer aumentar suas habilidades RxJS ao longo do tempo, a fim de usar de forma HttpClienteficaz.
Se você estiver acompanhando esses snippets de código, observe que deve importar os símbolos observáveis e de operador RxJS que aparecem nesses snippets. Essas ConfigServiceimportações são típicas.
Além de buscar dados do servidor, HttpClientsuporta solicitações mutantes, isto é, enviando dados para o servidor com outros métodos HTTP, como PUT, POST e DELETE.
O aplicativo de amostra deste guia inclui uma versão simplificada do exemplo "Tour of Heroes", que busca heróis e permite que os usuários os adicionem, excluam e atualizem.
Muitos servidores exigem cabeçalhos extras para operações de salvaguarda. Por exemplo, eles podem exigir um cabeçalho "Content-Type" para declarar explicitamente o tipo MIME do corpo da solicitação. Ou talvez o servidor precise de um token de autorização.
Decorador que marca um campo de classe como uma propriedade de entrada e fornece metadados de configuração. A propriedade input está vinculada a uma propriedade DOM no modelo. Durante a detecção de alterações, o Angular atualiza automaticamente a propriedade de dados com o valor da propriedade DOM.
Você pode fornecer um nome opcional para usar em modelos quando o componente é instanciado, que é mapeado para o nome da propriedade associada. Por padrão, o nome original da propriedade associada é usado para ligação de entrada.
O exemplo a seguir cria um componente com duas propriedades de entrada, uma das quais recebe um nome de ligação especial.
@Component({
selector: 'bank-account',
template: `
Bank Name: {{bankName}}
Account Id: {{id}}
`
})
class BankAccount {
// This property is bound using its original name.
@Input() bankName: string;
// this property value is bound to a different property name
// when this component is instantiated in a template.
@Input('account-id') id: string;
// this property is not bound, and is not automatically updated by
// Angular
normalizedBankName: string;
}
@Component({
selector: 'app',
template: `
<bank-account bankName="RBC" account-id="4747"></bank-account>
`
})
class App {}
O Firebase é uma plataforma do Google que contém várias ferramentas e uma excelente infraestrutura para ajudar desenvolvedores web e mobile a criar aplicações de alta qualidade e performance.
Esta plataforma contém quatro seguimentos de serviços: Analytics, Develop, Grow e Earn. Veja um pouco sobre cada um deles.
O serviço em nuvem para desenvolvedores móveis é um back-end completo para aplicações mobile (Android e iOS) e aplicações web. Com visual limpo e de uso simples, o Firebase é uma plataforma dedicada e SDK para a construção de aplicativos. Atualmente, o serviço suporta desenvolvimento nas linguagens de programação C++, Java, Javascript, Node.js, Objective-C e Swift.
Google está se transformando o Firebase em uma plataforma de aplicativos unificada para para seus mais de 470 mil desenvolvedores. A ferramenta apresenta agora um serviço de análise profundamente integrado, que foi construído pela mesma equipe que é responsável pelo Google Analytics.
Esta plataforma contém quatro seguimentos de serviços:
Analytics,
Develop,
Grow e
Earn.
Veja um pouco sobre cada um deles.
O Firebase Analytics é uma solução gratuita e ilimitada, considerado o coração do Firebase, é utilizado para gerar as métricas da aplicação, mensurar o comportamento do usuário. Atualmente é disponibilizado para aplicações iOS e Android.
Com a missão de poupar tempo e fornecer um aplicativo de alta qualidade, esta plataforma contém vários recursos para os desenvolvedores, são eles:
Nem todos os recursos para desenvolvedores são disponibilizados em todas as plataformas (Android, iOS, web), para resumir, é possível ver no quadro abaixo a relação de Recurso x Plataforma:!
Além de vários recursos para auxiliar no desenvolvimento das aplicações, o Firebase também disponibiliza recursos voltados ao envolvimento e conquista dos usuários para a aplicação, estes recursos são:
• Notifications: Através deste recurso é possível gerenciar campanhas de notificações para seu app e quando integrado ao Firebase Analytics é possível entregar mensagens a um segmento específico de usuários.
• App Indexing: Com o App Indexing você consegue aumentar a visibilidade do seu app em pesquisas do Google e do Now on Tap em dispositivos Android. E um recurso interessante é que os usuários ao buscarem um conteúdo relacionado eles poderão iniciar o aplicativo diretamente dos resultados de busca, se app estiver instalado no dispositivo, e caso não esteja, é exibido uma opção para instalação do aplicativo.
• Invites: O Invites, é uma solução desenvolvida para indicações e compartilhamento de aplicativos. Permite que os usuários do app compartilhem o aplicativo ou o conteúdo por e-mail ou SMS.
• AdWords: Este recurso vinculado ao Firebase Analytics permite que você mostre anúncios direcionados a segmentos de usuários, assim é possível otimizar o desempenho de sua campanha de forma eficaz.
Para lucrar com seus aplicativos através da exibição de anúncios, o Firebase disponibiliza o AdMob. Com ele é possível monetizar seus apps mobile com publicidade segmentada dentro do aplicativo e assim gerar receita sem prejudicar a experiência do usuário.
O Firebase fornece tudo que você precisa para desenvolver aplicações web e mobile, desde o desenvolvimento e testes até a publicação e divulgação do aplicativo.
E para utilizar esse serviço, tudo o que os desenvolvedores precisam fazer é adicionar algumas linhas de código nos aplicativos. Com isso, informações básicas do usuário serão transmitidas para o Firebase. Assim como com o Google Analytics, os desenvolvedores podem ter um instrumento específico em partes de seus aplicativos, com eventos apurados para controlar, por exemplo, sempre que um botão for pressionado ou uma compra for feita.
Usando esses dados, por meio do Google Firebase você pode construir segmentos de público e permitir que desenvolvedores analisem o comportamento de seus usuários em mais detalhes, vendo como suas campanhas publicitárias estão funcionando, por exemplo.
Além disso, o sistema de notificação do Firebase, o Cloud Messaging, oferece a todos os usuários notificações gratuitas e ilimitadas, com suporte para iOS, Android e na web. A ferramenta também permite que os devs saibam quando uma aplicação sua teve comportamento inesperado no smartphone do usuário, tornando mais fácil solucionar falhas em novas atualizações do app.
Variaveis do Firebase:
• auth: É o usuário autenticado
• data: São os dados existentes no caminho, por exemplo, pessoa/idade
• newData: São os dados postados no caminho. Esse variável só está disponível em .write e .validate pois somente nesses momentos que novos dados serão postados
• now: É uma marcação de data e hora de tempo real do servidor
• root: Levará de volta a raiz do banco de dados
• $: Curinga, como usamos em $uid para pegar o ID do usuário do registro
O Firebase Hosting fornece hospedagem rápida e segura para seu aplicativo Web, conteúdo estático e dinâmico e microsserviços. O Firebase Hosting é um host de nível de produção para desenvolvedores. Com um único comando, você pode implantar rapidamente aplicativos da Web e veicular conteúdo estático e dinâmico em uma CDN global (rede de entrega de conteúdo). Você também pode emparelhar o Firebase Hosting com o Cloud Functions ou o Cloud Run para criar e hospedar microsserviços no Firebase.
Servir conteúdo por uma conexão segura | A web moderna é segura. O SSL de configuração zero é incorporado ao Firebase Hosting, para que o conteúdo seja sempre entregue com segurança. |
Hospede conteúdo estático e dinâmico, além de microsserviços | O Firebase Hosting suporta todos os tipos de conteúdo para hospedagem, dos arquivos CSS e HTML aos microsserviços ou APIs do Express.js. |
Entregue conteúdo rapidamente | Cada arquivo que você carrega é armazenado em cache nos SSDs nas bordas da CDN em todo o mundo. Não importa onde seus usuários estejam, o conteúdo será entregue rapidamente. |
Implantar novas versões com um comando | Usando a Firebase CLI, você pode colocar seu aplicativo em funcionamento em segundos.As ferramentas de linha de comando facilitam a adição de destinos de implantação ao seu processo de criação. |
Reversão com um clique | As implantações rápidas são ótimas, mas ser capaz de desfazer erros é ainda melhor. O Firebase Hosting fornece gerenciamento completo de versão e versão com reversões de um clique. |
O Firebase Hosting foi desenvolvido para o desenvolvedor web moderno. Sites e aplicativos estão mais poderosos do que nunca com o surgimento de estruturas JavaScript front-end, como ferramentas de gerador de angular e estática, como Jekyll. Esteja você implantando uma página de entrada de aplicativo simples ou um PWA (Progressive Web App) complexo, o Hosting fornece a infraestrutura, os recursos e as ferramentas personalizadas para implantar e gerenciar sites e aplicativos.
Usando a Firebase CLI , você implanta arquivos de diretórios locais no seu computador no servidor Hosting. Além de exibir conteúdo estático, você pode usar o Cloud Functions for Firebase ou Cloud Run para exibir conteúdo dinâmico e hospedar microsserviços em seus sites. Todo o conteúdo é veiculado por uma conexão SSL do servidor de borda mais próximo em nossa CDN global.
O Firebase Hosting possui opções de configuração de hospedagem leves para você criar PWAs sofisticados. Você pode reescrever facilmente URLs para roteamento do lado do cliente ou configurar cabeçalhos personalizados.
Para veicular seu conteúdo, o Firebase oferece várias opções de domínio e subdomínio:
Por padrão, todo projeto do Firebase possui subdomínios gratuitos nos domínios web.appe firebaseapp.com. Esses dois sites atendem ao mesmo conteúdo e configuração implantados.
Você pode criar vários sites se tiver sites e aplicativos relacionados que exibem conteúdo diferente, mas ainda compartilhem os mesmos recursos do projeto Firebase (por exemplo, se você possui um blog, painel de administração e aplicativo público).
Você pode conectar seu próprio nome de domínio a um site hospedado no Firebase.
O Firebase provisiona automaticamente certificados SSL para todos os seus domínios, para que todo o seu conteúdo seja veiculado com segurança.
https://console.firebase.google.com
Clicar em adicionar projeto.
Digitar o nome do projeto. Clicar em Continuar.
Desmarcar a opção do Google Analitics e clicar em Criar seu Projeto
Aguardar criar o projeto
Projeto Concluido. Clicar em continuar
Fomos direcionados para o Painel de Controle do projeto.
Clicar no icone de web </> para podermos pegar o script de configuração do projeto com o firebase.
Registrar o app. Digitar o nome do projeto.
Clicar em Registrar app.
Clicar em proxima
Clicar na engrenagem, do lado do icone de Visão Geral do Projeto
Clicar em Configuração do Projeto
Descer até Apps da Web e clicar em CDN
Copiar o script da configuração do Firebase.
.
No menu, clicar em Cloud Firestore.
.
Entraremos na área de criação das collections.
.
Clicar em iniciar coleção para criarmos a collection produtos
(lembrando que é no plural). Digitar o nome e clicar em proxima
.
Clicar em codigo automatico para gerar o id
da collection e digitar o nome dos campos com seus respectivos valor para podermos inserir um novo documento.
.
Para adicionar mais campos, clicar e, adicionar campo. Adicionar todos os campos e clicar em salvar
.
Aguardar criar a collection e o documento. É possivel adicionar campos, editar ou excluir.
.