Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
117 changes: 44 additions & 73 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,74 +1,45 @@
# Desafio para Flutter Developer na DoroTech
# Projeto
OBS: Devido ao prazo em que tive para entregar o projeto, o aplicativo ficou bem corrido, com possibilidades de melhoria, especialmente com relação ao visual das telas (comecei fazendo pequenos pedaços em intervalos no trabalho, e foquei depois das 18 até o horário limite 23:59).
Algumas ideias deixarei com (*) representando ações que foram afetadas por causa da entrega

## Como padrão, comecei o desenvolvimento criando as pastas que pensei necessárias para o projeto quando fosse inicializa-lo, são essas:

### **/assets**: De inicio criei a pasta aqui para deixar vários arquivos SVG afim de deixar o aplicativo com uma cara moderna e amigável(*)
### **/core**: Aonde ficarão objetos necessários para a aplicação, como:
* Os dados do aplicativo;
* Arquivos de cache;
* Algumas strigns usadas em vários lugares na aplicação (Ideal seria deixar um arquivo em core com as strings mais utilizadas e um arquivo especifico em cada feature (*))
* Funções e Widgets que podem ser usados em toda a aplicação
## **/features**: Aqui estão todas as telas na aplicação, as pastas padrões são:
#### /controller: com os controllers da das telas responsáveis pelo gerenciamento de estado das telas
#### /repository: arquivos para fazer acesso aos dados que serão consumidos pelos controller e presenter
#### /presenter: telas e widgets em si
#### algumas telas podem ter mais pastas, como:
#### - /data: aonde ficarão objetos que somente aquele recurso deve consumir
#### - /componets: local aonde podem ficar alguns widgets ou recursos mais genéricos para a feature (*)

## test
- **/test** a pasta de test deve seguir as mesmas estruturas que a pasta de produção (/lib)]

Com as pastas criadas comecei a implementa-las, começando pela /core, com as classes que seriam necessárias para a aplicação
Em segundo momento, busquei criar algumas classes abstratas que seriam uteis em breve já criando seus mocks para testes
Em seguida, comecei desenvolvendo os testes da classe de controller, garantindo que suas funções estejam fazendo suas responsabilidades
Após os testes, comecei a realizar a criação das telas e testar as classes repositories na produção, felizmente funcionaram de primeira.

Para realizar o desafio tive a ajuda de algumas bibliotecas que costumo utilizar:
- Hive: Para cache, consigo salvar classes inteiras em cache de forma fácil, a utilizo muito para criar micro-frontends no meu trabalho.
- MobX: Gerencimento de estado das telas, fiz a implementação de forma rápida, sem utilizar muitos de seus recursos, poderia ter ficado melhor, em alguns lugares utilizei também o setState(*)
- http: Realizar conexões com a API
- path_provide: Utilizada para obter o diretório da aplicação no device para o Hive salvar a os objetos da forma como implementei
- connectivity_plus: Verificar o device está com dados móveis ou Wi-Fi ativo
- material_design_icons_flutter: Icones
- test, mockito, faker: Auxiliar nos testes.
- flutter_native_splash: Criar uma tela nativa de splash screen básica
- flutter_launcher_icons: Adicionar logo no ícone ao aplicativo

### Para compilar
- **web** pode-se user flutter run -d chrome
- **android** deixarei um apk na pasta raiz, caso não execute, pode rodar com flutter run --release

Versão do Flutter utilizada: Flutter 3.3.10

Somos uma empresa com clientes que atuam em vários segmentos do mercado, com diferentes tecnologias, culturas e desafios.

Gostamos de compor nossos times com profissionais multidisciplinares, que tenham alta capacidade de aprendizado, sejam detalhistas, resilientes, questionadores e curiosos.
Você, como **Flutter Developer**, será o responsável por implementar, dar manutenção, aplicar correções e propor soluções em projetos de software.

## Orientações
Para executar o desafio de **Flutter Developer**, você **deverá utilizar framework Flutter e seguir suas boas práticas**, seguindo o [passo a passo](https://github.com/dorotech/flutter-test#etapas) para a execução, atendendo aos [critérios de aceitação](https://github.com/dorotech/flutter-test#critérios-de-aceitação).

## Desafio
Nossa equipe é apaixonada por **Rick and Morty**, o seu desafio será criar uma aplicação utilizando a API pública da série [https://rickandmortyapi.com/](https://rickandmortyapi.com/), para exibir a lista de personagens.
Veja a documentação [https://rickandmortyapi.com/documentation/#rest](https://rickandmortyapi.com/documentation/#rest).

Os requisitos da aplicação:

- Como usuário, desejo visualizar na página inicial, uma lista de 20 personagens incialmente, contendo **foto**, **nome** e **status**, com o tamanho da paginação sendo dinamica, podendo ser selecionando, 5, 10 ou 20 itens por vez.
- Como usuário, desejo clicar em um personagem da lista, para visualizar informações detalhadas. (seja criativo a api contem diversas informaçoes)
- Como usuário, desejo filtrar os personagens por **nome**, **gênero**, **espécie** e **status**, alguns filtros são enums, seja criativo.
- Como usuário, desejo combinar varios filtros.

## Etapas

#### 1 - Fazer um fork desse repositório

#### 2 - Criar um branch com o seu primeiro e último nome
```bash
git checkout -b joao-silva
```

#### 3 - Escreva a documentação da sua aplicação
Você deve, substituir o conteúdo do arquivo **README.md** e escrever a documentação da sua aplicação, com os seguintes tópicos:
- **Projeto**: Descreva o projeto e como você o executou. Seja objetivo.
- **Tecnologias**: Descreva quais tecnologias foram utilizadas, enumerando versões (se necessário) e os links para suas documentações, quais bibliotecas instalou e porque.
- **Como compilar e rodar**: Descreva como compilar e rodar sua aplicação no Android e Web

#### 4 - Faça uma Pull Request
Após implementada a solução, crie uma [pull request](https://github.com/dorotech/flutter-test/pulls) com o seu projeto para esse repositório, avise o recrutador.

## Critérios de Aceitação
Para que seu teste tenha o mínimo necessário que atenda aos requisitos esperados, ele deve:
- Atender ao que foi proposto no [Desafio](https://github.com/dorotech/flutter-test#Desafio).
- Interfaces responsivas compatíveis com dispositivos Mobile e Web.
- Especificar qual dispositivo foi utilizado para testar a aplicação.
- Compatibilidade entre browsers.
- Uso de alguma arquitetura para o código. Ex: MVVM, BLoC.
- Utilizar padrões semânticos em mensagens de commit. (Gostamos do padrão de commits do repositório [AngularJS](http://karma-runner.github.io/3.0/dev/git-commit-msg.html))
- Caso você nao consiga completar tudo e tenha algum receio, não se preocupe, iremos avaliar o que foi entregue, mesmo com pendências.
- O diferencial para este desafio: layout, ux e ui, bem como implementação de boas práticas de segurança, performance e/ou estrutura.


## Dicas e Informações Valiosas

#### O que gostaríamos de ver em seu teste:
- Convenção de nome em classes, objetos, variáveis, métodos e etc.
- layout encantador
- Faça commits regulares. Eles são melhores do que um commit gigantesco. Gostaríamos de ver commits organizados e padronizados, então capriche neles!
- Animações, Sombras, Menus, componentes de Libs de UX implementados.
- **Bônus 1** Dark Mode, implementação sendo um botão que mude o padrão de cores da pagina para escuro e claro com 1 click ou que siga a configuração do dispositivo do cliente.
- **Bônus 2** Listagem de favoritos, com algum mecanismo de cache.
- **Bônus 3** Outros filtros além dos sugeridos na descrição inicial
- **Bônus 4** Testes automatizados

**Observação:** Nenhum dos itens acima é obrigatório.

#### O que o seu Teste não deve ter:
- Saber que não foi você quem implementou o projeto.
- Varias bibliotecas instaladas sem uso.
- Falta de organização de código.
- Falta de documentação.
- Nome de variáveis sem sentido ou sem padrão de nomes.
- Histórico de commits desorganizado e despadronizado.

## Boa Sorte!!
Binary file added apk/app-release.apk
Binary file not shown.
44 changes: 44 additions & 0 deletions rick_and_morty_app/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
# Miscellaneous
*.class
*.log
*.pyc
*.swp
.DS_Store
.atom/
.buildlog/
.history
.svn/
migrate_working_dir/

# IntelliJ related
*.iml
*.ipr
*.iws
.idea/

# The .vscode folder contains launch configuration and tasks you configure in
# VS Code which you may wish to be included in version control, so this line
# is commented out by default.
#.vscode/

# Flutter/Dart/Pub related
**/doc/api/
**/ios/Flutter/.last_build_id
.dart_tool/
.flutter-plugins
.flutter-plugins-dependencies
.packages
.pub-cache/
.pub/
/build/

# Symbolication related
app.*.symbols

# Obfuscation related
app.*.map.json

# Android Studio will place build artifacts here
/android/app/debug
/android/app/profile
/android/app/release
45 changes: 45 additions & 0 deletions rick_and_morty_app/.metadata
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
# This file tracks properties of this Flutter project.
# Used by Flutter tool to assess capabilities and perform upgrades etc.
#
# This file should be version controlled.

version:
revision: 135454af32477f815a7525073027a3ff9eff1bfd
channel: stable

project_type: app

# Tracks metadata for the flutter migrate command
migration:
platforms:
- platform: root
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: android
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: ios
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: linux
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: macos
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: web
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd
- platform: windows
create_revision: 135454af32477f815a7525073027a3ff9eff1bfd
base_revision: 135454af32477f815a7525073027a3ff9eff1bfd

# User provided section

# List of Local paths (relative to this file) that should be
# ignored by the migrate tool.
#
# Files that are not part of the templates will be ignored by default.
unmanaged_files:
- 'lib/main.dart'
- 'ios/Runner.xcodeproj/project.pbxproj'
16 changes: 16 additions & 0 deletions rick_and_morty_app/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# rick_and_morty_app

A new Flutter project.

## Getting Started

This project is a starting point for a Flutter application.

A few resources to get you started if this is your first Flutter project:

- [Lab: Write your first Flutter app](https://docs.flutter.dev/get-started/codelab)
- [Cookbook: Useful Flutter samples](https://docs.flutter.dev/cookbook)

For help getting started with Flutter development, view the
[online documentation](https://docs.flutter.dev/), which offers tutorials,
samples, guidance on mobile development, and a full API reference.
29 changes: 29 additions & 0 deletions rick_and_morty_app/analysis_options.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# This file configures the analyzer, which statically analyzes Dart code to
# check for errors, warnings, and lints.
#
# The issues identified by the analyzer are surfaced in the UI of Dart-enabled
# IDEs (https://dart.dev/tools#ides-and-editors). The analyzer can also be
# invoked from the command line by running `flutter analyze`.

# The following line activates a set of recommended lints for Flutter apps,
# packages, and plugins designed to encourage good coding practices.
include: package:flutter_lints/flutter.yaml

linter:
# The lint rules applied to this project can be customized in the
# section below to disable rules from the `package:flutter_lints/flutter.yaml`
# included above or to enable additional rules. A list of all available lints
# and their documentation is published at
# https://dart-lang.github.io/linter/lints/index.html.
#
# Instead of disabling a lint rule for the entire project in the
# section below, it can also be suppressed for a single line of code
# or a specific dart file by using the `// ignore: name_of_lint` and
# `// ignore_for_file: name_of_lint` syntax on the line or in the file
# producing the lint.
rules:
# avoid_print: false # Uncomment to disable the `avoid_print` rule
# prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule

# Additional information about this file can be found at
# https://dart.dev/guides/language/analysis-options
13 changes: 13 additions & 0 deletions rick_and_morty_app/android/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
gradle-wrapper.jar
/.gradle
/captures/
/gradlew
/gradlew.bat
/local.properties
GeneratedPluginRegistrant.java

# Remember to never publicly share your keystore.
# See https://flutter.dev/docs/deployment/android#reference-the-keystore-from-the-app
key.properties
**/*.keystore
**/*.jks
71 changes: 71 additions & 0 deletions rick_and_morty_app/android/app/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
def localProperties = new Properties()
def localPropertiesFile = rootProject.file('local.properties')
if (localPropertiesFile.exists()) {
localPropertiesFile.withReader('UTF-8') { reader ->
localProperties.load(reader)
}
}

def flutterRoot = localProperties.getProperty('flutter.sdk')
if (flutterRoot == null) {
throw new GradleException("Flutter SDK not found. Define location with flutter.sdk in the local.properties file.")
}

def flutterVersionCode = localProperties.getProperty('flutter.versionCode')
if (flutterVersionCode == null) {
flutterVersionCode = '1'
}

def flutterVersionName = localProperties.getProperty('flutter.versionName')
if (flutterVersionName == null) {
flutterVersionName = '1.0'
}

apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle"

android {
compileSdkVersion flutter.compileSdkVersion
ndkVersion flutter.ndkVersion

compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}

kotlinOptions {
jvmTarget = '1.8'
}

sourceSets {
main.java.srcDirs += 'src/main/kotlin'
}

defaultConfig {
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
applicationId "com.example.rick_and_morty_app"
// You can update the following values to match your application needs.
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-build-configuration.
minSdkVersion flutter.minSdkVersion
targetSdkVersion flutter.targetSdkVersion
versionCode flutterVersionCode.toInteger()
versionName flutterVersionName
}

buildTypes {
release {
// TODO: Add your own signing config for the release build.
// Signing with the debug keys for now, so `flutter run --release` works.
signingConfig signingConfigs.debug
}
}
}

flutter {
source '../..'
}

dependencies {
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
}
8 changes: 8 additions & 0 deletions rick_and_morty_app/android/app/src/debug/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.rick_and_morty_app">
<!-- The INTERNET permission is required for development. Specifically,
the Flutter tool needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->
<uses-permission android:name="android.permission.INTERNET"/>
</manifest>
36 changes: 36 additions & 0 deletions rick_and_morty_app/android/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.rick_and_morty_app">
<uses-permission android:name="android.permission.INTERNET" />

<application
android:label="Rick and Morty"
android:name="${applicationName}"
android:icon="@mipmap/launcher_icon">
<activity
android:name=".MainActivity"
android:exported="true"
android:launchMode="singleTop"
android:theme="@style/LaunchTheme"
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated="true"
android:windowSoftInputMode="adjustResize">
<!-- Specifies an Android theme to apply to this Activity as soon as
the Android process has started. This theme is visible to the user
while the Flutter UI initializes. After that, this theme continues
to determine the Window background behind the Flutter UI. -->
<meta-data
android:name="io.flutter.embedding.android.NormalTheme"
android:resource="@style/NormalTheme"
/>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<!-- Don't delete the meta-data below.
This is used by the Flutter tool to generate GeneratedPluginRegistrant.java -->
<meta-data
android:name="flutterEmbedding"
android:value="2" />
</application>
</manifest>
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package com.example.rick_and_morty_app

import io.flutter.embedding.android.FlutterActivity

class MainActivity: FlutterActivity() {
}
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading