Similar presentations:
Разработка мобильного приложения «Выставка собак»
1.
Министерство образования и науки Челябинской областигосударственное бюджетное профессиональное образовательное учреждение
«Саткинский горно-керамический колледж имени А.К.Савина»
Разработка мобильного приложения “Выставка собак”
По учебной дисциплине «РПМ»
Работа сделал Долинни Д.Ю
2. Актуальность мобильного приложения
Выставка собак становится интерактивным шоу благодаря приложению с картой и расписанием. Вовлечениезрителей через голосование повышает привлекательность мероприятия и расширяет аудиторию.
Приложение
автоматизирует
оповещения,
объединяя
регистрацию
участников
в
и
едином
цифровом пространстве. Это делает мероприятия
комфортнее и отвечает потребностям цифровизации
кинологической отрасли.
3.
Цель проектаРазработка приложения для сквозной автоматизации выставочных мероприятий: от подачи заявки владельцем
до ветеринарного контроля и финального учета организаторами.
Для поставленной цели были решены следующие задачи:
1.Спроектирована база данных (ER-модель в нотации IDEF1X) и
реализована в SQL Server 2019.
2.Разработан интерфейс мобильного приложения в Figma.
3.Создано мобильное приложение на Java в Android Studio.
4.Обеспечено взаимодействие с БД PostgreSQL через API (FastAPI).
5.Реализованы модули управления профилями (животные, клиенты,
сотрудники, выставки).
6.Выполнено тестирование и составлена инструкция для пользователя.
4. Выбор и обоснование стека технологий
5. Разработка интерфейса
6. Разработка базы данных
7. Разработка API
@app.route('/api/clients', methods=['GET', 'POST'])Разработка API
def handle_clients():
"""Обрабатывает GET и POST запросы для клиентов (получение списка или добавление)"""
# Проверяем токен авторизации
token = request.headers.get('Authorization', '').replace('Bearer ', '')
if not verify_token(token):
return jsonify({'success': False, 'message': 'Недействительный токен'}), 401
# В зависимости от метода вызываем соответствующую функцию
if request.method == 'GET':
return get_clients()
elif request.method == 'POST':
"""Создает JWT токен для аутентификации пользователя"""
return add_client()
try:
def get_clients():
payload = {
'sub': phone_number, # subject - номер телефона
Листинг 1 - Эндпоинты для работы с клиентами
пользователя
'exp': datetime.utcnow() + timedelta(hours=24) # срок
действия 24 часа
# Сложный запрос с JOIN для получения имен владельца и ветеринара
}
cur.execute('''
# Кодируем токен с секретным ключом
SELECT a.animal_id, a.name, a.age, a.gender, a.breed,
token = jwt.encode(payload, SECRET_KEY,
a.description, a.mother_id, a.father_id,
algorithm='HS256')
a.vet_id, a.owner_id,
# Преобразуем в строку, если получен байтовый формат
c.last_name || ' ' || c.first_name as owner_name,
if isinstance(token, bytes):
e.last_name || ' ' || e.first_name as vet_name
return token.decode('utf-8')
FROM animals a
return str(token)
LEFT JOIN clients c ON a.owner_id = c.client_id
except Exception as e:
LEFT JOIN employees e ON a.vet_id = e.employee_id
print(f"Token creation error: {e}")
ORDER BY a.name
return None
''')
animals_data = cur.fetchall()
animals = []
Листинг 2 - Эндпоинты для работы с животными
Листинг 3 - Функции для работы с паролями и токенами
8. Разработка программного кода
private void setupBottomNavigation() {bottomNavigationView.setOnNavigationItemSelectedListener(item ->
{
currentFragmentId = item.getItemId();
Fragment selectedFragment = null;
String title = "";
// Определение выбранного пункта меню
if (item.getItemId() == R.id.nav_animals) {
selectedFragment = new AnimalsFragment();
title = "Животные";
} else if (item.getItemId() == R.id.nav_exhibitions) {
selectedFragment = new ExhibitionsFragment();
title = "Выставки";
} else if (item.getItemId() == R.id.nav_employees) {
selectedFragment = new EmployeesFragment();
title = "Сотрудники";
} else if (item.getItemId() == R.id.nav_clients) {
selectedFragment = new ClientsFragment();
title = "Клиенты";
}
Листинг 1 - настройка навигации в MainActivity
private void registerUser() {
// Получение данных из полей ввода
String phoneNumber = etPhoneNumber.getText().toString().trim();
String password = etPassword.getText().toString().trim();
String confirmPassword = etConfirmPassword.getText().toString().trim();
// Валидация введенных данных
if (!validateInput(phoneNumber, password, confirmPassword)) {
return;
}
// Создание запроса к API
ApiService apiService = RetrofitClient.getInstance().getApiService();
Call<AuthResponse>
call
=
apiService.register(new
AuthRequest(phoneNumber, password));
Листинг 2 - Регистрация пользователя в RegisterActivity
private Animal createAnimalObject(String name, int age, String gender, String breed,
String description, Integer motherId, Integer fatherId,
int vetId, int ownerId) {
Animal animal = new Animal();
animal.setName(name);
animal.setAge(age);
animal.setGender(gender);
animal.setBreed(breed);
animal.setDescription(description);
animal.setMotherId(motherId);
animal.setFatherId(fatherId);
animal.setVetId(vetId);
animal.setOwnerId(ownerId);
return animal;
}
Листинг 3 - Создание объекта животного AddEditAnimalActivity
9. Разработка программного кода
@Overrideprotected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_clients);
// Инициализация SharedPreferences
sharedPreferences = getSharedPreferences("auth", Context.MODE_PRIVATE);
// Инициализация View элементов
recyclerView = findViewById(R.id.recyclerView);
Button btnAddClient = findViewById(R.id.btnAddClient);
// Настройка RecyclerView
setupRecyclerView();
// Настройка обработчика для кнопки добавления клиента
btnAddClient.setOnClickListener(v -> {
Intent intent = new Intent(ClientsActivity.this, AddEditClientActivity.class);
startActivity(intent);
});
// Загрузка списка клиентов
loadClients();
}
Листинг 2 – Методы жизненного цикла в AddEditEmployeeActivity
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_add_edit_employee);
// Инициализация
sharedPreferences = getSharedPreferences
("auth", Context.MODE_PRIVATE);
// Инициализация UI компонентов
etLastName = findViewById(R.id.etLastName);
etFirstName = findViewById(R.id.etFirstName);
etMiddleName = findViewById(R.id.etMiddleName);
etAddress = findViewById(R.id.etAddress);
etPosition = findViewById(R.id.etPosition);
etSalary = findViewById(R.id.etSalary);
Button btnSave = findViewById(R.id.btnSave);
// Проверка режима редактирования
if (getIntent().hasExtra("employee")) {
isEditMode = true;
currentEmployee = (Employee) getIntent().getSerializableExtra("employee");
fillData();
}
Листинг 1 - Метод onCreate - инициализация активности в ClientsActivity
// Получение данных из полей ввода
String lastName = etLastName.getText().toString().trim();
String firstName = etFirstName.getText().toString().trim();
String middleName =
etMiddleName.getText().toString().trim();
String address = etAddress.getText().toString().trim();
String phoneNumber =
etPhoneNumber.getText().toString().trim();
Листинг 3 – Метод сохранения данных в AddEditClientActivity
programming