mirall: (job)
Также между делом стало понятно, почему в Scala, в отличие от всех нормальных языков, к элементам массива обращаются через круглые, а не квадратные скобки. Потому что это, блин, тоже функция. I love this language, though it crashes and breaks my brain to pieces.

А ещё сегодня попался Scala код, написанный Java-программистом. Настолько очевидно, что вот именно сел человек и написал кусок кода этим своим java-ориентированным стилем. Просто синтаксис другой. Как подстрочник стихов, сделанный автоматическим переводчиком. Так же режет взгляд и оскорбляет чувство прекрасного.
mirall: (job)
Книжка про Big Data architectural principles. Введение. Длинный и драматический рассказ о том, как обычно строят приложение, в основе которого лежит реляционная СУБД, и о том, как она неизбежно становится единой точкой отказа.

One problem is that your database is not self-aware of its distributed nature, so it can't help you deal with shards, replication, and distributed queries. All that complexity got pushed to you both in operating the database and developing the application code.

Дьявольщина, так возьми СУБД, которая поддерживает собственную распределёность и делает это прозрачно для приложения. Такие есть и даже больше, чем одна.

А потом мы плавно переехали на Big Data.

Another core technique you'll learn about is making you data immutable. Instead of storing the counts as your core dataset, which you continuously mutate as new record to count comes in, you store the raw record information. It is never modified. So when you make a mistake, you might write bad data, but at least you won't destroy good data.

Плохой, плохой архитектор баз данных. Кто тебя учил делать update на количество записей? Изменений данных вообще лучше избегать. Чем меньше операций update в коде, тем лучше.

Нет, я всё понимаю, новая модная перспективная технология. И сейчас нас быстренько научат выжать из неё всё. Но, чёрт побери, если ты не умеешь проектировать приложения на основе реляционных СУБД, то реляционные СУБД в этом не виноваты. Просто у кого-то кривые руки. Впрочем, как всегда.
mirall: (job)
Если ты не в состоянии придумать новому методу короткое внятное имя, вероятнее всего ты написал хреновый метод.
mirall: (job)
dbms_sql.bind_variable поддерживает пользовательские типы, varray и nested table.

А я-то с этим багом два дня мучилась.
mirall: (job)
Когда нельзя в RAISE использовать переменные, а можно только строки-константы. Что вообще за идиотская практика хардкодить сообщения об ошибках в хранимых процедурах?
mirall: (job)
Дано.
Лес (т.е. набор деревьев) простого алгоритма представлен в виде двух таблиц.

       Table "algorithm_node"
    Column    |       Type        | Modifiers
--------------+-------------------+-----------
 node_id      | ext_id_udt        | not null
 algorithm_id | ext_id_udt        | not null
 node_type    | character varying | not null
Indexes:
    "algorithm_node_pk" PRIMARY KEY, btree (node_id, algorithm_id)

    Table "algorithm_node_link"
       Column        |    Type    | Modifiers
---------------------+------------+-----------
 algorithm_id        | ext_id_udt | not null
 source_node_id      | ext_id_udt | not null
 destination_node_id | ext_id_udt | not null
Indexes:
    "algorithm_node_link_pk" PRIMARY KEY, btree (algorithm_id, source_node_id, destination_node_id)
Foreign-key constraints:
    "alg_node_link_dst__alg_node_fk" FOREIGN KEY (destination_node_id, algorithm_id)
          REFERENCES algorithm_node(node_id, algorithm_id)
    "alg_node_link_src__alg_node_fk" FOREIGN KEY (source_node_id, algorithm_id)
          REFERENCES algorithm_node(node_id, algorithm_id)

По алгоритму задаётся некая функциональность. При этом любые ноды алгоритма могут быть в функциональности пропущены.

                   Table "program_node"
         Column         |           Type           | Modifiers
------------------------+--------------------------+-----------
 program_node_id        | id_udt                   | not null
 program_id             | id_udt                   | not null
 algorithm_node_id      | ext_id_udt               | not null
 algorithm_id           | ext_id_udt               | not null
 state                  | ref_id_udt               | not null
Indexes:
    "program_node_pk" PRIMARY KEY, btree (program_node_id)
Foreign-key constraints:
    "prg_node__alg_node_fk" FOREIGN KEY (algorithm_node_id, algorithm_id)
          REFERENCES algorithm_node(node_id, algorithm_id)

Задача состояла в том, чтобы вернуть корни функциональности. Получилось такое безобразие.

with recursive rec (node_id, parent_id, program_node_id, nx, program_id) as (
  select lb.node_id, lb.parent_id, lb.program_node_id, lb.n nx, lb.program_id program_id
    from link lb
    where lb.parent_id is null
  union
  select l.node_id, l.parent_id, l.program_node_id, rec.nx + l.n, l.program_id
    from link l join rec on (rec.node_id = l.parent_id) 
),
link as (
  select an.node_id node_id, aln.source_node_id parent_id, pnd.program_node_id
       , case when pnd.program_node_id is null then 0 else 1 end n, pnd.program_id
    from algorithm.algorithm_node an
    left join algorithm.algorithm_node_link aln on aln.destination_node_id = an.node_id
    left join task.program_node pnd on an.node_id = pnd.algorithm_node_id
                                and pnd.program_id = 'ALG1' and pnd.state = 0
    where an.algorithm_id = rt_prg.algorithm_id
)
select program_node_id from rec r
  where nx = 1
    and program_node_id is not null

В целом, ничего выдающегося. За исключением того, что я в равной степени плохо разбираюсь в рекурсивных запросах и в PostgreSQL. Список личных мелких открытий:
1) если хочется в одном запросе использовать обычный и рекурсивный WITH, то сначала пишется рекурсивный, а потом только обычный;
2) PostgreSQL поддерживает аналитические функции (здесь не используется, но как-то мимоходом выяснилось);
3) придумывать рекурсивные запросы - это не просто долго, это очень долго, по крайней мере, для мозга, не привыкшего мыслить рекурсивно.
mirall: (Default)
Регулярно забываю, что Oracle Database 11.2, вообще-то, под Windows 7 не сертифицирован, а потому ошибки установки неизбежны как завтрашний день.
mirall: (Default)
Повторно влетела спустя ровно год.
http://longbowgirl.livejournal.com/430638.html
mirall: (Default)
Надо всё бросать и перечитывать "Thinking in Java". И перечитывать, и перечитывать. Пока концепция не утрамбуется хотя бы чуточку. Потому что пока что мозг рвётся на запчасти и непонятно ничего.

Какой ужас - переход от реляционного и процедурного мышления к объектно-ориентированному.
mirall: (job)
Проблема была в следующем.
При подключении к RAC под пользователем sys, рандомно выпадала ошибки ORA-01017: invalid username/password; logon denied. Т.е. десять коннектов подряд могли семь раз соединиться нормально и три раза упасть.

Коллеги почему-то начали рыть в области case sensitivity имён пользователей в Oracle. "А может такое быть, что sys и SYS - это разные пользователи". По мне, такого быть не может.

А оказалось, что почему-то на разных экземплярах были выставлены разне пароли для sys. Когда подключение направлялось на первый узел кластера, коннектилось нормально. На второй - падало с ошибкой.

Пароль-то вернули на место. Но у меня до сих пор в голове не укладыватся, как такое возможно. Похоже, я в RAC понимаю ещё меньше, чем думала.
mirall: (job)
Не знаю, зачем её гасили, но завести снова не смогли.
Симптомы

$ srvctl start database -d ractest1
PRCR-1079 : Failed to start resource ora.ractest1.db
ORA-00119: invalid specification for system parameter %s
CRS-2674: Start of 'ora.ractest1.db' on 'racnode01' failed
CRS-2632: There are no more servers to try to place resource 'ora.ractest1.db' on that would satisfy its placement policy
ORA-00119: invalid specification for system parameter %s
CRS-2674: Start of 'ora.ractest1.db' on 'racnode02' failed

Мутно и невнятно. Лог сообщал, что USER (ospid: 4216): terminating the instance due to error 119 (за pid не поручусь, но смысл именно такой).

Путём несложных преобразований (старт экземпляра локально из sqlplus, свежеобретённый полный, а не ссылочный pfile) выяснилось, что всё плохо в области remote_listener, каковой, вообще-то, был, по идее, в порядке, т.е. содержал нужное значение hostname:port.

Дальше я пошла кружным путём: ковыряла spfile. Сбросила remote_listener, после чего база завелась, но к ней всё ещё невозможно было подконнектиться. Попутно обнаружилось, что spfile проехал почему-то не из ASM, а из файловой системы. Пофиксилось пересозданием.

Потом попыталась вернуть remote_listener к исходному значению, не удалось, hostname базе всё ещё не нравился. Зато именно в этот момент начали падать осмысленные ошибки, которые уже нормально гуглились.

В результате обнаружилось, что в sqlnet.ora на обоих узлах должно быть прописано NAMES.DIRECTORY_PATH=(TNSNAMES,EZCONNECT), а у нас было NAMES.DIRECTORY_PATH=(TNSNAMES). Смешно и неудобно. Несколько часов возни, а в результате - изменить одну строчку.

Digest

Apr. 21st, 2011 07:22 pm
mirall: (job)
    Первый раз в жизни поставила CPU в день релиза. Правда, зачем-то скачала патч для версии 11.2.0.2 и долго пыталась понять, почему же он у меня не становится. Пока не сообразила, что у меня-то стоит 11.2.0.1. Милое дело эти патчи. Если бы всё так ставилось с полпинка.

    Неожиданно, совершенно неожиданно data pump начал падать со страшненькой ошибкой
UDE-31623: операция сгенерировала ошибку ORACLE 31623
ORA-31623: задание не присоединено к этому сеансу через заданный указатель

    В скобках. Зачем я когда-то настроила русскую локаль, до сих пор не пойму.
    Так об ошибке. Она начала падать после аварийного прерывания собственно импорта. Т.е. что-то у меня там импортировалась, я нажала Ctrl+C, операция завершилась. Следующий импорт торжественно упал. Точно так же падает и экспорт. Информации по ошибке — мизер. Два варианта решения проблемы и ни один мне не подходит.
    А не написать ли в support?
mirall: (job)
Вы устали получать ошибки ora-01502? Ваш индекс в статусе unusable?
Перестройте его!
mirall: (job)
    Имеется задача: организовать нагрузочное тестирование базы Oracle XE. Полдня думаю, как с этим бороться. Real Application Testing, кажется, работает только в EE версии 11g (хотя попробовать, конечно, можно). EM для XE куцый и подробных статистических отчётов в себя не включает. На этом идеи закончились.
    А, между прочим, в понедельник уже нужно представить хотя бы проект решения. И как дальше жить?
mirall: (Default)
    В процессе попыток скомпилировать существующий код в Oracle XE (10.2.0.1) обнаружила одну неприятную особенность: возможность создания объекта только через позиционную нотацию. Т.е. вместо
select my_object (num_val => t.num_val, str_val => t.str_val) from my_table t
приходится использовать
select my_object (t.num_val, t.str_val) from my_table t
    Это мелочь, если объекты маленькие. А у меня попадаются экземпляры на двадцать атрибутов.
    И ещё всякое )
mirall: (job)
    Загвоздка была (совершенно классически) в том, что несколько процессов одновременно пытались редактировать одну и ту же строку в таблице.
    Процедура, о которую споткнулось приложение, принимала на вход сложный объект с атрибутами-массивами, данные из которых нужно было разложить по таблицам.
    Первый вариант реализации был прост и незатейлив: существовала отдельная процедура, которая записывала результат для одной строки, и вызывалась в цикле (не оптимально, но удобно). Споткнулись о deadlock.
    Второй вариант: заменила цикл на bulk merge (до вчерашнего дня и не подозревала, что bulk merge возможен наравне с bulk insert и bulk update). Не помогло. Вернее помогло частично: deadlock стал появляться не сразу, а через минуту где-то после запуска приложения.
    Собралась с силами, переделала bulk merge в merge по select * from table (input_array). И, похоже, сработало. По крайней мере, тесты, оставленные гоняться ночью, ошибок не выкинули.
    Мораль сей басни такова. Циклы must die — это раз. Bulk update/merge имеет смысл использовать только если обычный update/merge ну никак невозможен — это два.
    Побочный эффект, который ещё придётся преодолеть: массив там не просто массив, а массив сложных объектов, каждый из которых также имеет атрибут-массив, который тоже нужно сохранить. Так что пора изобрести какой-то волшебный способ сделать прямой select из этого массива. Чем сейчас и займусь.
mirall: (job)
    Влетела сегодня в восхитительнейший deadlock. Третий час ломаю голову, что я могла такое нахимичить и откуда подобные выкрутасы. Притом что концептуально приложение не поменялось. По сути, (если раскопки завели в ту степь) ошибка упирается в факт, что один столбец переехал из дочерней таблицы в родительскую. Переехать её что ли обратно?
mirall: (job)
Много букв )
mirall: (job)
    Business logic = all about data.
    Application logic = not all about data, all about making it look pretty.
    Business logic should be kept in database. Application logic should be kept outside it.
mirall: (job)
    Вообще говоря, типичный копипаст. Но я с ним провозилась довольно долго, так что микроотчёт.
    Немного текста и чуть-чуть скриптов )

Profile

mirall: (Default)mirall

July 2017

S M T W T F S
      1
2345678
9101112131415
16171819202122
23242526272829
3031     

Syndicate

RSS Atom

Style Credit

Expand Cut Tags

No cut tags
Page generated Sep. 25th, 2017 06:07 am
Powered by Dreamwidth Studios